Answers:
从2016年开始,您应该为此使用Array.findIndex
(ES2015 / ES6标准):
a = [
{prop1:"abc",prop2:"qwe"},
{prop1:"bnmb",prop2:"yutu"},
{prop1:"zxvz",prop2:"qwrq"}];
index = a.findIndex(x => x.prop2 ==="yutu");
console.log(index);
Google Chrome,Firefox和Edge支持该功能。对于Internet Explorer,在链接页面上有一个polyfill。
业绩说明
函数调用是昂贵的,因此对于非常大的数组,简单的循环将比findIndex
:
let test = [];
for (let i = 0; i < 1e6; i++)
test.push({prop: i});
let search = test.length - 1;
let count = 100;
console.time('findIndex/predefined function');
let fn = obj => obj.prop === search;
for (let i = 0; i < count; i++)
test.findIndex(fn);
console.timeEnd('findIndex/predefined function');
console.time('findIndex/dynamic function');
for (let i = 0; i < count; i++)
test.findIndex(obj => obj.prop === search);
console.timeEnd('findIndex/dynamic function');
console.time('loop');
for (let i = 0; i < count; i++) {
for (let index = 0; index < test.length; index++) {
if (test[index].prop === search) {
break;
}
}
}
console.timeEnd('loop');
与大多数优化一样,应谨慎且仅在实际需要时才应用此优化。
x => x.prop2=="yutu"
findIndex()的工作原理吗?
function(x) { return x.prop2=="yutu" }
index = a.findIndex(function (x) { return x.prop2 == "yutu" })
改正为已解决的问题,以便使用polyfill代码,findIndex在IE11中起作用
我如何获取对象的索引与条件匹配(不沿数组迭代)?
您不能,某些东西必须遍历数组(至少一次)。
如果条件变化很大,那么您将不得不遍历并查看其中的对象,以查看它们是否符合条件。但是,在具有ES5功能(或如果您安装垫片)的系统上,可以相当简洁地完成该迭代:
var index;
yourArray.some(function(entry, i) {
if (entry.prop2 == "yutu") {
index = i;
return true;
}
});
该Array#some
函数使用new(ish)函数,该函数会循环访问数组中的条目,直到为您提供的函数返回true。我给它的函数保存了匹配条目的索引,然后返回true
以停止迭代。
或者,当然,只需使用for
循环即可。您的各种迭代选项将在此其他答案中介绍。
但是,如果您总是要使用相同的属性进行查找,并且属性值是唯一的,则可以循环一次并创建一个对象来映射它们:
var prop2map = {};
yourArray.forEach(function(entry) {
prop2map[entry.prop2] = entry;
});
(或者再次,您可以使用for
循环或任何其他选项。)
然后,如果您需要使用查找条目prop2 = "yutu"
,则可以执行以下操作:
var entry = prop2map["yutu"];
我称此为“交叉索引”数组。自然,如果删除或添加条目(或更改其prop2
值),则也需要更新映射对象。
thg435
做了我想要的...
TJ Crowder所说的,总是会有某种隐藏的迭代,用lodash变成:
var index = _.findIndex(array, {prop2: 'yutu'})
var index;
yourArray.some(function (elem, i) {
return elem.prop2 === 'yutu' ? (index = i, true) : false;
});
遍历数组的所有元素。如果条件不匹配,则返回索引,则返回true或false。
重要的是显式返回值true(或布尔结果为true的值)。由于可能的索引为0(Boolean(0)=== false),单次分配是不够的,这不会导致错误,但会禁用迭代中断。
编辑
甚至更短的版本:
yourArray.some(function (elem, i) {
return elem.prop2 === 'yutu' && ~(index = i);
});
~
它将无法正常工作。
!!(index = 0)
和!!~(index = 0)
差异确实如此。谢谢!
您可以通过以下方式使用Array.prototype.some()(如其他答案中所述):
https://jsfiddle.net/h1d69exj/2/
function findIndexInData(data, property, value) {
var result = -1;
data.some(function (item, i) {
if (item[property] === value) {
result = i;
return true;
}
});
return result;
}
var data = [{prop1:"abc",prop2:"qwe"},{prop1:"bnmb",prop2:"yutu"},{prop1:"zxvz",prop2:"qwrq"}]
alert(findIndexInData(data, 'prop2', "yutu")); // shows index of 1
我在上面看到了许多解决方案。
在这里,我正在使用map函数在数组对象中查找搜索文本的索引。
我将使用学生数据来解释我的答案。
步骤1:为学生创建数组对象(可选,您可以创建自己的数组对象)。
var students = [{name:"Rambabu",htno:"1245"},{name:"Divya",htno:"1246"},{name:"poojitha",htno:"1247"},{name:"magitha",htno:"1248"}];
第2步:创建变量以搜索文本
var studentNameToSearch = "Divya";
步骤3:创建变量以存储匹配的索引(这里我们使用map函数进行迭代)。
var matchedIndex = students.map(function (obj) { return obj.name; }).indexOf(studentNameToSearch);
var students = [{name:"Rambabu",htno:"1245"},{name:"Divya",htno:"1246"},{name:"poojitha",htno:"1247"},{name:"magitha",htno:"1248"}];
var studentNameToSearch = "Divya";
var matchedIndex = students.map(function (obj) { return obj.name; }).indexOf(studentNameToSearch);
console.log(matchedIndex);
alert("Your search name index in array is:"+matchedIndex)
function findIndexByKeyValue(_array, key, value) {
for (var i = 0; i < _array.length; i++) {
if (_array[i][key] == value) {
return i;
}
}
return -1;
}
var a = [
{prop1:"abc",prop2:"qwe"},
{prop1:"bnmb",prop2:"yutu"},
{prop1:"zxvz",prop2:"qwrq"}];
var index = findIndexByKeyValue(a, 'prop2', 'yutu');
console.log(index);
您为什么不想精确地迭代?新的Array.prototype.forEach非常适合此目的!
如果需要,可以使用二进制搜索树通过单个方法调用进行查找。这是JS中BTree和Red black搜索树的巧妙实现-https: //github.com/vadimg/js_bintrees-但我不确定是否可以同时找到索引。
使用Array.reduce()的第一步-没有jQuery
var items = [{id: 331}, {id: 220}, {id: 872}];
var searchIndexForId = 220;
var index = items.reduce(function(searchIndex, item, index){
if(item.id === searchIndexForId) {
console.log('found!');
searchIndex = index;
}
return searchIndex;
}, null);
null
如果找不到索引,将返回。
var list = [
{prop1:"abc",prop2:"qwe"},
{prop1:"bnmb",prop2:"yutu"},
{prop1:"zxvz",prop2:"qwrq"}
];
var findProp = p => {
var index = -1;
$.each(list, (i, o) => {
if(o.prop2 == p) {
index = i;
return false; // break
}
});
return index; // -1 == not found, else == index
}
试试这个代码
var x = [{prop1:"abc",prop2:"qwe"},{prop1:"bnmb",prop2:"yutu"},{prop1:"zxvz",prop2:"qwrq"}]
let index = x.findIndex(x => x.prop1 === 'zxvz')
0
?上找到)。两种解决方案的迭代次数都超过了所需的迭代次数,如果数组很大(虽然人们可能会注意到这样大的几率很低,除非查找发生得很多),则迭代效果不理想。