最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

jquery - How to get the JSON with duplicate keys completely in javascript - Stack Overflow

programmeradmin3浏览0评论

I am trying to get JSON from the url, But in the response object duplicate keys are removed. Is there any way to fetch it pletely without removing the duplicate keys? Here is my js Code

$('document').ready(function(){
    var s = $.getJSON("new.json");
    console.log(s);
});

following is my new.json

{
"s": "wae",
"s": "asd"
}

But in console i am getting the json Object as follows

responseJSON: Object
s: "asd"

Thanks in advance

I am trying to get JSON from the url, But in the response object duplicate keys are removed. Is there any way to fetch it pletely without removing the duplicate keys? Here is my js Code

$('document').ready(function(){
    var s = $.getJSON("new.json");
    console.log(s);
});

following is my new.json

{
"s": "wae",
"s": "asd"
}

But in console i am getting the json Object as follows

responseJSON: Object
s: "asd"

Thanks in advance

Share Improve this question edited Jun 15, 2015 at 10:28 Callum Linington 14.4k14 gold badges79 silver badges156 bronze badges asked Jun 15, 2015 at 10:18 SajuSaju 611 gold badge1 silver badge4 bronze badges 2
  • 4 The only way would be to parse the JSON manually (as in, fetch the JSON as normal text) – Prisoner Commented Jun 15, 2015 at 10:22
  • Indeed. You'll have to write a custom JSON parser from scratch (unless someone else has published one, but I'm not away of any examples and library remendations are off-topic here anyway). That's probably too broad a subject for Stackoverflow. – Quentin Commented Jun 15, 2015 at 10:32
Add a ment  | 

5 Answers 5

Reset to default 3

If you can't change the server response, for simple JSON data you can request the json like text and parse it like a string:

var check = new RegExp('["\']([^\'"]*)[\'"][^:]*:[^"\']*["\']([^\'"]*)[\'"]',"g");
    $.ajax({
        url : "text.json",
        dataType : "text",
        success : function(data){
            var newData = {};
            data.replace(check,function(a,b,c){
                if(typeof newData[b] == "undefined"){
                    newData[b] = c;
                }else if(typeof newData[b] == "object"){
                    newData[b].push(c);
                }else{
                    var ca = newData[b];
                    newData[b] = [ca,c];                     
                }
                return a;
            });
            console.log(newData);
            console.log($.parseJSON(data));
        },
        error : function(e,a){
            console.log(e,a);
        }
    });

in this code newData with your json is:

{"s": ["wae","asd"]}

Keys in a JSON object should be unique. Otherwise the last key with the value is usually the one presented when requesting that key. Having keys the same also makes it more difficult to differentiate between attributes of an object. The whole point of a key is to make it accessible and available.

To get around this you could always:

  1. Change the keys in your JSON

  2. Change the JSON to contain an array

    {"s": ["wae","asd"]}

The JavaScript Object Notation (JSON) Data Interchange Format) (RFC7159) says:

The names within an object SHOULD be unique.

In this context should must be understood as specified in RFC 2119

SHOULD This word, or the adjective "RECOMMENDED", mean that there may exist valid reasons in particular circumstances to ignore a particular item, but the full implications must be understood and carefully weighed before choosing a different course.


RFC 7159 explains why unique keys are good: > An object whose names are all unique is interoperable in the sense > that all software implementations receiving that object will agree on > the name-value mappings. When the names within an object are not > unique, the behavior of software that receives such an object is > unpredictable. Many implementations report the last name/value pair > only. Other implementations report an error or fail to parse the > object, and some implementations report all of the name/value pairs, > including duplicates. > > JSON parsing libraries have been observed to differ as to whether > or not they make the ordering of object members visible to calling > software. Implementations whose behavior does not depend on member > ordering will be interoperable in the sense that they will not be > affected by these differences.

This is not possible with JSON.parse(). I believe that the more modern ES spec states that subsequent keys override earlier ones.

However, the JSON spec does not disallow JSON like this. And there are alternative parsers and serializers which can produce and consume such JSON from within JavaScript. For example, you can use the SAX-style JSON parser clarinet:

const clarinet = require('clarinet');

const parser = clarinet.parser();
const result = [];
parser.onkey = parser.onopenobject = k => {
    result.push({key: k, value: null});
};
parser.onvalue = v => {
    result[result.length - 1].value = v;
};
parser.write('{"a": "1", "a": "2"}').close();

console.log(result);
// [ { key: 'a', value: '1' }, { key: 'a', value: '2' } ]

If you are wondering about how to use require() from the browser, learn how to use webpack.

JSON allows duplicates keys but Javascript Objects do not.

Because keys can be duplicated, that means the JSON cannot be represented as key/value based dictionary and cannot be converted directly to a Javascript Object.

You will have to "walk" through each key/value pair in the JSON and then process it as you see fit. I don't know what structure you are looking to convert into, but it as long as it's not a Javascript Object, then it's fine. For example, you might walk through a JSON object and output the values to an .ini or .css file where "keys" can be repeated.

JSON.parse() will not work because that will try to parse into a Javascript Object, which does not allow duplicated keys. The solution there is to simply overwrite any previous value if the key is reused. But, we can use code based on how JSON.parse() works and instead of setting properties on a Javascript Object, you can split from there and apply your custom solution.

You can modify a plete JSON parser like json2 or use parsers that stream keys as they arrive like clarinet or Oboe.js.

You may try using given structure to use same key multiple times:

[
  {"s": "wae"},
  {"s": "asd"}
]

As suggested by Craicerjack, you can also go for array for multiple values with single key:

{"s": ["wae","asd"]}
发布评论

评论列表(0)

  1. 暂无评论