javascript 如何从对象文字数组中切片数组?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/10827894/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-26 11:11:37  来源:igfitidea点击:

How do I slice an array from an array of object literals?

javascriptarrayssortingsliceobject-literal

提问by Ian Campbell

I have this array, in which each index contains an object literal. All of the object literals have the same properties. Some of the object literals have the same value for a given property, and I want to create a new array containing onlythose object literals.

My idea is to sort the array, and slice it into a new array...

Here is the array:

我有这个数组,其中每个索引都包含一个对象文字。所有对象字面量都具有相同的属性。对于给定的属性,某些对象文字具有相同的值,我想创建一个包含这些对象文字的新数组。

我的想法是对数组进行排序,并将其切片成一个新数组......

这是数组:

var arr = [];

arr[0] =
{
    country: "United States",
    num: 27
};

arr[1] =
{
    country: "Australia",
    num: 5
};

arr[2] =
{
    country: "United States",
    num: 7
};


So, I want to create a new array containing only those objects where the property countryis "United States". This is my crazy idea so far, which doesn't work:


因此,我想创建一个仅包含属性country为“美国”的对象的新数组。到目前为止,这是我的疯狂想法,但行不通:

function getNewArray(arr)
{
    var arr2 = [];

    for(var key in arr)
    {
        for(var i = 0; i < arr.length - 1; i++)
        {
            if(arr.hasOwnProperty(key) && arr[i].name == arr[i + 1].name)
            {
                    arr2[i] = arr.slice(key);
            }
        }
    }

    return arr2;
}

var arr3 = getNewArray(arr).sort();

采纳答案by elclanrs

var getCountry = function (country) {
    var out = [];
    for (var i = 0, len = arr.length; i < len; i++)
        if (arr[i].country === country) out.push(arr[i]);
    return out;
};

Demo:http://jsfiddle.net/YwytD/1/

演示:http : //jsfiddle.net/YwytD/1/

回答by nnnnnn

"I want to create a new array containing only those objects where the property country is "United States""

“我想创建一个新数组,只包含属性国家为“美国”的那些对象”

This is exactly what the Array.filter()methodis for:

这正是该Array.filter()方法的用途:

var filteredArray = arr.filter(function(val, i, a) {
                                  return val.country==="United States";
                    });

Note that the .filter()method isn't available in IE before version 9, but the MDN page I linked to above shows you exactly how to implement it so reading that page should in itself answer your question.

请注意,该.filter()方法在版本 9 之前的 IE 中不可用,但我上面链接的 MDN 页面向您展示了如何实现它,因此阅读该页面本身应该可以回答您的问题。

Note also that in the (non-working) code in the question, your two forloops are basically doing the same thing as each other because they're both iterating over arr, so it doesn't make sense to nest them like that. You shouldn't use a for..in loop on an array, but if you do the keyvalues will be the numeric indexes, it doesn't somehow pick up the properties of the object stored at each index.

另请注意,在问题中的(非工作)代码中,您的两个for循环基本上彼此执行相同的操作,因为它们都在迭代arr,因此像这样嵌套它们是没有意义的。您不应该在数组上使用 for..in 循环,但如果您这样做,则key值将是数字索引,它不会以某种方式获取存储在每个索引处的对象的属性。

EDIT:

编辑:

"Some of the object literals have the same value for a given property, and I want to create a new array containing only those object literals."

“对于给定的属性,某些对象文字具有相同的值,我想创建一个仅包含这些对象文字的新数组。”

OK, re-reading this I guess you didn't really want to select elements by specifying a country, you wanted to select elements for any country that had duplicate entries? So if there were another three elements that all had "New Zealand" you'd want to select them in additionto the "United States" ones? If so, you could do something like this:

好的,重新阅读本文,我猜您并不是真的想通过指定国家/地区来选择元素,而是想为任何具有重复条目的国家/地区选择元素?因此,如果还有另外三个元素都包含“新西兰”,那么除了“美国”元素之外,您还想选择它们吗?如果是这样,你可以这样做:

var countryCount = {},
    i;
for (i = 0; i < arr.length; i++)
    if (countryCount.hasOwnProperty(arr[i].country)
       countryCount[arr[i].country]++;
    else
       countryCount[arr[i].country] = 1;

var filteredArr = arr.filter(function(val, i, a) {
                      return countryCount[val.country] > 1;
                  });

回答by Rishi Diwan

There is a simpler way of doing this, I think this is what you want var new_arr = arr.filter(function(obj){ return obj['country'] === 'United States'; })This will filter your results into new_arr Of course you can make it better and more generic than just 'United States'

有一种更简单的方法可以做到这一点,我认为这就是您想要的 var new_arr = arr.filter(function(obj){ return obj['country'] === 'United States'; })这会将您的结果过滤为 new_arr 当然,您可以使它比“美国”更好,更通用

Edit: Whoops, got your question just now

编辑:哎呀,刚刚得到你的问题

Answer: Nested Filters :)

答案:嵌套过滤器 :)

function getKeyStuff(key) {
    return arr.filter( function(obj) { 
        var new_arr = arr.filter( function(inner_obj) { 
            return inner_obj[key] === obj[key]; 
        });
        return new_arr.length > 1; 
    });
}

回答by ziad-saab

Here is my solution:

这是我的解决方案:

// assuming arr is already set

var num_obj = arr.length;
var obj_by_country = {}, obj;
for (var i = 0; i < num_obj; i++) {
  obj = arr[i];
  if (!obj_by_country[obj.country]) {
    obj_by_country[obj.country] = [];
  }
  obj_by_country[obj.country].push(obj);
}

// build final array
var final_array = [];
for (i in obj_by_country) {
  if (obj_by_country[i].length > 1) {
    final_array.push(obj_by_country[i]);
  }
}

回答by ltiong_sh

Can you use JQuery?

你可以使用 JQuery 吗?

var arr = [];
arr[0] = { country: "United States", num: 27 };
arr[1] = { country: "Australia", num: 5 };
arr[2] = { country: "United States", num: 7 };

var newArray = [];
$.each(arr, function(){
   if(this.country == "United States")
      newArray.push(this);
});

回答by MiGnH

getByKey = function(arr, key, value) {
    var results = [];
    for(var i = 0; i < arr.length; i++) {
       if(arr[i][key] === value) {
           results.push(arr[i]);
       }
    }
    return results
}

here's a working example http://jsfiddle.net/michaelghayes/UyHYz/2/

这是一个工作示例 http://jsfiddle.net/michaelghayes/UyHYz/2/