How to get the JSON with duplicate keys completely in javascript

前端 未结 5 1609
后悔当初
后悔当初 2020-11-30 13:07

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 completely without removing the duplicate keys? Her

相关标签:
5条回答
  • 2020-11-30 13:33

    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 complete JSON parser like json2 or use parsers that stream keys as they arrive like clarinet or Oboe.js.

    0 讨论(0)
  • 2020-11-30 13:38

    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"]}
    
    0 讨论(0)
  • 2020-11-30 13:40

    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.

    0 讨论(0)
  • 2020-11-30 13:49

    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.

    0 讨论(0)
  • 2020-11-30 13:52

    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 讨论(0)
提交回复
热议问题