简体   繁体   English

从json获取特定数据

[英]Get specific data from json

I have a variable json that contains some json data. 我有一个包含一些json数据的变量json。 I am trying to retrieve a specific part of that data. 我正在尝试检索该数据的特定部分。 I can do it using the index like shown here: 我可以使用如下所示的索引来完成它:

var newdata = json[listid].Taxonomies[0];

However I want to be able to retrieve the data using a name... For example I want to get the data where 但是我希望能够使用名称检索数据...例如,我想将数据放在哪里

json[listid].Taxonomies[?].InternalName = 'ABC'

and I don't know the value of '?' 我不知道'?'的价值

Is there a way I can do this without doing an each loop on the taxonomies? 有没有办法在不对分类法进行每个循环的情况下做到这一点?

This can't be done without looping, but libraries exist that hide that looping from you. 如果没有循环,这是不可能完成的,但是存在隐藏循环的库。

For example, using JSPath you can find every instance of the InternalName property regardless of how deeply nested it is: 例如,使用JSPath,您可以找到InternalName属性的每个实例,无论它的嵌套程度如何:

> var json = { 1: { Taxonomies: [ { InternalName: 'ABC' } ] }}
> JSPath.apply('..InternalName', json);
["ABC"]

Some people suggested linqjs, and that may be OK if you need a lot of JSON querying. 有些人建议使用linqjs,如果你需要大量的JSON查询,这可能没问题。 However, for this problem, you can use the Array.filter to specify which item to find. 但是,对于此问题,您可以使用Array.filter指定要查找的项目。 Obviously, there's still a loop under the hood. 显然,引擎盖下还有一个循环。

var matches  = json[listid].Taxonomies.filter(function(obj) {
    return obj.InternalName === "ABC";
})

console.log(matches[0]);

http://jsfiddle.net/MC94q/ http://jsfiddle.net/MC94q/

Note that if you are worried about performance, you should use an object instead of an array for your data representation, and you can key it by the property you'll be searching by. 请注意,如果您担心性能,则应使用对象而不是数组来表示数据,并且可以通过要搜索的属性对其进行键入。

A useful function I use if I need to search multiple times on an array is the following. 如果我需要在阵列上多次搜索,我使用的有用功能如下。 This transforms the array into a map that can be accessed without loops. 这会将数组转换为可以在没有循环的情况下访问的映射。 And if you're worried about performance, just generate the data in that format instead if you can. 如果您担心性能问题,请尽可能以该格式生成数据。

/**
 * Creates a map by the given property to allow fast searches
 * @param {object[]} arr Array that we want to create a map from
 * @param {string} keyProp The property to key by
 * @param {boolean} [allowDuplicates] If this is true, the value
 *        of each key in the returned object will be an array with 
 *        all matches
 * @return A map keyed by the requested property. If the parameter 
 *         allowDuplicates is falsy, key property collisions will 
 *         overwrite the previous value. If the allowDuplicates is true,
 *         the map will have as its value an array of objects for the given key
 *
 * Example: Given the following array: arr=[{a:1, b:2}, {a:1, b:3}, {a:3, b:4)]
 *   The call to mapFromArray(arr, 'a') returns the following
 *          { 1: {a:1, b:3}, 3: {a:3, b:4} }
 *   Notice that {a:1,b:2} is not in the returned map because it has the 
 *   same value in the key property 'a' as {a:1, b:3}, which wins out 
 *   since it's later.
 *
 *   Calling  mapFromArray(arr, 'a', true) returns the following
  *         { 1: [{a:1, b:2}, {a:1, b:3}], 3: [{a:3, b:4}] }
 */
function mapFromArray(arr, keyProp, allowDuplicates) {
    var map = {};
    for (var i = 0, ln = arr.length; i < ln; i++) {
        if (!allowDuplicates) {
            // No duplicates allowed, may be overwriting an existing value
            map[arr[i][keyProp]] = arr[i];
        } else {
            // Duplicates are allowed, create array of matching objects
            // Ext.Array.push creates a one item array if its argument is
            // not already an array, otherwise, it pushes and returns the array
            map[arr[i][keyProp]] = Ext.Array.push(map[arr[i][keyProp]], arr[i]);
        }
    }
    return map;
}

So say you wanted to search for taxonomies with InternalName of one of 'ABC' 'DEF' 'GHI', you would do the following: 所以说你想搜索InternalName为'ABC''DEF''GHI'之一的分类法,你会做以下事情:

var map = mapFromArray(json[listid].Taxonomies, "InternalName");
var ABC = map['ABC'], DEF = map['DEF'], GHI = map['GHI'];
var newdata = json[listid].Taxonomies.filter(function(el){
  return el.InternalName === "ABC";
})[0];

Should cover the first occurence of an object like that. 应该涵盖像这样的物体的第一次出现。 If you want an array of all the occurrences you can remove the [0] at the end. 如果需要所有出现的数组,可以删除末尾的[0]

Note that I'm assuming a single nesting level, since thats how the question is phrased. 请注意,我假设一个嵌套级别,因为这就是问题的措辞。 If you need to find the property in an arbitrary deep data structure, some of the other libraries here might make more sense. 如果需要在任意深度数据结构中找到属性,这里的一些其他库可能更有意义。

The first thing that comes to mind is something like linqjs ( http://linqjs.codeplex.com/ ). 首先想到的是像linqjs( http://linqjs.codeplex.com/ )。 Here's an example given your inputs. 这是给出输入的一个例子。

var jsonArray = [
    { "listid": 1, 
     Taxaonomies:
        [ 
            { "id": 100, "InternalName": "d_linq" },
            { "id": 200, "InternalName": "fred" }
        ]
    },
    { "listid": 2, 
        Taxaonomies:
        [ 
            { "id": 100, "InternalName": "asdf" },
            { "id": 200, "InternalName": "qwer" }
        ]
    }
];

var queryResult = Enumerable.From(jsonArray)
    .Where(function (x) { 
        return Enumerable.From(x.Taxaonomies).Any(function (y) { return y.InternalName == "fred" }) 
    })
    .ToArray();

console.log(queryResult);

See this fiddle: http://jsfiddle.net/alexdresko/3zsy9/ 看到这个小提琴: http//jsfiddle.net/alexdresko/3zsy9/

You can use the JQuery Javascript library to parse the JSON into an object. 您可以使用JQuery Javascript库将JSON解析为对象。 From there you can access properties with the dot syntax. 从那里,您可以使用点语法访问属性。

http://api.jquery.com/jQuery.parseJSON/ http://api.jquery.com/jQuery.parseJSON/

var obj = jQuery.parseJSON('{"name":"Bob"}');
alert(obj.name === "Bob");

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM