type - javascript object




檢查JavaScript對像中是否存在密鑰? (13)

如何檢查JavaScript對像或數組中是否存在特定鍵?

如果某個密鑰不存在,並且我嘗試訪問它,它會返回false嗎? 或者拋出錯誤?


ES6解決方案

使用Array#someObject.keys 。 如果對像中存在給定鍵,則返回true ,否則返回false

var obj = {foo: 'one', bar: 'two'};
    
function isKeyInObject(obj, key) {
    var res = Object.keys(obj).some(v => v == key);
    console.log(res);
}

isKeyInObject(obj, 'foo');
isKeyInObject(obj, 'something');

單行示例。

console.log(Object.keys({foo: 'one', bar: 'two'}).some(v => v == 'foo'));


快速回答

如何檢查JavaScript對像或數組中是否存在特定鍵? 如果某個密鑰不存在而我嘗試訪問它,它會返回false嗎? 或者拋出錯誤?

使用(關聯)數組樣式或對像樣式直接訪問缺少的屬性將返回未定義的常量。

運算符和hasOwnProperty方法中的緩慢可靠

正如人們在這裡已經提到的那樣,你可以擁有一個具有與“未定義”常量相關聯的屬性的對象。

 var bizzareObj = {valid_key:  undefined};

在這種情況下,您將必須使用hasOwnProperty運算符中知道密鑰是否確實存在。 但是, 但是以什麼價格?

所以,我告訴你......

operator和hasOwnProperty中是在Javascript中使用屬性描述符機制的“方法”(類似於Java語言中的Java反射)。

http://www.ecma-international.org/ecma-262/5.1/#sec-8.10

屬性描述符類型用於解釋命名屬性屬性的操作和具體化。 屬性描述符類型的值是由命名字段組成的記錄,其中每個字段的名稱是屬性名稱,其值是8.6.1中指定的對應屬性值。 此外,可以存在或不存在任何字段。

另一方面,調用對象方法或鍵將使用Javascript [[Get]]機制。 那要快得多!

基準

http://jsperf.com/checking-if-a-key-exists-in-a-javascript-array

運營商中使用
var result = "Impression" in array;

結果是

12,931,832 ±0.21% ops/sec      92% slower 
使用hasOwnProperty
var result = array.hasOwnProperty("Impression")

結果是

16,021,758 ±0.45% ops/sec     91% slower
直接訪問元素(括號樣式)
var result = array["Impression"] === undefined

結果是

168,270,439 ±0.13 ops/sec     0.02% slower 
直接訪問元素(對像樣式)
var result = array.Impression  === undefined;

結果是

168,303,172 ±0.20%     fastest

編輯:為屬性分配undefined值的原因是什麼?

那個問題困擾著我。 在Javascript中,缺少對象的至少兩個引用可以避免這樣的問題: nullundefined

null是原始值,表示故意缺少任何對象值,或者簡稱為確認的缺乏值。 另一方面, undefined是未知值(未定義)。 如果稍後將使用具有適當值的屬性,請考慮使用null引用而不是undefined因為在最初時刻,屬性被確認為缺少值。

相比:

var a = {1: null}; 
console.log(a[1] === undefined); // output: false. I know the value at position 1 of a[] is absent and this was by design, i.e.:  the value is defined. 
console.log(a[0] === undefined); // output: true. I cannot say anything about a[0] value. In this case, the key 0 was not in a[].

勸告

避免使用undefined值的對象。 盡可能直接檢查並使用null初始化屬性值。 否則,使用slow in運算符或hasOwnProperty()方法。

編輯:12/04/2018 - 不相關任何人

正如人們所評論的那樣,現代版本的Javascript引擎(使用firefox異常)改變了訪問屬性的方法。 對於這種特定情況,當前實現比前一個實現慢,但是訪問密鑰和對象之間的差異是可忽略的。


對於那些在項目中包含lodash
有一個lodash _.get方法試圖獲得“深”鍵:

獲取object對象的值。 如果未定義已解析的值,則返回defaultValue。

var object = { 'a': [{ 'b': { 'c': 3 } }] };

console.log(
  _.get(object, 'a[0].b.c'),           // => 3
  _.get(object, ['a', '0', 'b', 'c']), // => 3
  _.get(object, 'a.b.c'),              // => undefined 
  _.get(object, 'a.b.c', 'default')    // => 'default'
)
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.4/lodash.min.js"></script>

這將有效地檢查是否定義了該密鑰(無論多麼深) ,並且如果未定義該密鑰,則不會拋出可能損害程序流的錯誤。


我們可以使用 - hasOwnProperty.call(obj, key);

underscore.js方式 -

if(_.has(this.options, 'login')){
  //key 'login' exists in this.options 
}

_.has = function(obj, key) {
  return hasOwnProperty.call(obj, key);
};

JavaScript解構的新解決方案:

var obj = {
    test: "",
    locals: {
        test: "",
        test2: false,
        test3: NaN,
        test4: 0,
        test5: undefined,
        auth: {
            user: "hw"
        }
    }
}

keyExistsOn(obj, "")
> false
keyExistsOn(obj, "locals.test")
> true
keyExistsOn(obj, "locals.test2")
> true
keyExistsOn(obj, "locals.test3")
> true
keyExistsOn(obj, "locals.test4")
> true
keyExistsOn(obj, "locals.test5")
> true
keyExistsOn(obj, "sdsdf")
false
keyExistsOn(obj, "sdsdf.rtsd")
false
keyExistsOn(obj, "sdsdf.234d")
false
keyExistsOn(obj, "2134.sdsdf.234d")
false
keyExistsOn(obj, "locals")
true
keyExistsOn(obj, "locals.")
false
keyExistsOn(obj, "locals.auth")
true
keyExistsOn(obj, "locals.autht")
false
keyExistsOn(obj, "locals.auth.")
false
keyExistsOn(obj, "locals.auth.user")
true
keyExistsOn(obj, "locals.auth.userr")
false
keyExistsOn(obj, "locals.auth.user.")
false
keyExistsOn(obj, "locals.auth.user")
true

請檢查JavaScript Destructuring的其他用法


回答:

if ("key" in myObj)
{
    console.log("key exists!");
}
else
{
    console.log("key doesn't exist!");
}

說明:

in運算符將檢查對像中是否存在鍵。 如果檢查了值是否未定義: if (myObj["key"] === 'undefined') ,則可能會遇到問題,因為對象可能存在undefined值的對象。

因此,最好先使用in運算符,然後在知道密鑰存在後比較密鑰內的值。



它將返回undefined

var aa = {hello: "world"};
alert( aa["hello"] );      // popup box with "world"
alert( aa["goodbye"] );    // popup box with "undefined"

undefined是一個特殊的常量值。 所以你可以說,例如

// note the three equal signs so that null won't be equal to undefined
if( aa["goodbye"] === undefined ) {
    // do something
}

這可能是檢查丟失密鑰的最佳方法。 但是,正如下面的評論所指出的那樣,理論上你可能希望將實際值undefinedundefined 。 我從來不需要這樣做,也無法想出為什麼我想要的原因,但為了完整起見,你可以使用in運算符

// this works even if you have {"goodbye": undefined}
if( "goodbye" in aa ) {
    // do something
}

最簡單的檢查方法是

let obj = {
    "key1": "value1",
    "key2": "value2",
    "key3": "value3",
};

let {key1, key2, key3, key4} = obj;

// key1 = "value1"
// key2 = "value2"
// key3 = "value3"
// key4 = undefined

// Can easily use `if` here on key4
if(!key4) { console.log("key not present"); } // Key not present

例如:

var keyExistsOn = (o, k) => k.split(".").reduce((a, c) => a.hasOwnProperty(c) ? a[c] || 1 : false, Object.assign({}, o)) === false ? false : true;

返回值為true意味著該鍵存在於對像中。


檢查javascript對像中是否存在屬性的三種方法:

  1. !obj.theProperty
    將值轉換為bool。 除“false”值之外的所有值都返回TRUE
  2. obj中的'theProperty'
    如果屬性存在,則返回true,無論其值如何(甚至為空)
  3. obj.hasOwnProperty('利人')
    不檢查原型鏈。 (因為所有對像都有'toString'方法,1和2將在其上返回true,而3可以在其上返回false。)

參考:

http://book.mixu.net/node/ch5.html


這些例子可以證明不同方式之間的差異。 希望它能幫助您選擇適合您需求的產品:

// Lets create object `a` using create function `A`
function A(){};
A.prototype.onProtDef=2;
A.prototype.onProtUndef=undefined;
var a=new A();
a.ownProp = 3;
a.ownPropUndef = undefined;

// Let's try different methods:

a.onProtDef; // 2
a.onProtUndef; // undefined
a.ownProp; // 3
a.ownPropUndef; // undefined
a.whatEver; // undefined
a.valueOf; // ƒ valueOf() { [native code] }

a.hasOwnProperty('onProtDef'); // false
a.hasOwnProperty('onProtUndef'); // false
a.hasOwnProperty('ownProp'); // true
a.hasOwnProperty('ownPropUndef'); // true
a.hasOwnProperty('whatEver'); // false
a.hasOwnProperty('valueOf'); // false

'onProtDef' in a; // true
'onProtUndef' in a; // true
'ownProp' in a; // true
'ownPropUndef' in a; // true
'whatEver' in a; // false
'valueOf' in a; // true (on the prototype chain - Object.valueOf)

Object.keys(a); // ["ownProp", "ownPropUndef"]

這是一個老問題,但我想永遠不會遲到給出答案。

想像一下,你有一個對象“產品”和兩個項目。 如果要查看此對像中是否已存在id,可以使用find()

products = [
    {
        "id": 1,
        "name": "Name 1"
    },
    {
        "id": 2,
        "name": "Name 2"
    },
  ]

  item1 = 
    {
        "id": 3,
        "name": "Name 3",
    }



  item2 = 
    {
        "id": 1,
        "name": "Name 1",
    }



  if(products.find(x => x.id === item1.id)){
    console.log('id is in products');
  }else {
    console.log('id is not in products');
  }
  if(products.find(x => x.id === item2.id)){
    console.log('id is in products');
  }else {
    console.log('id is not in products');
  }

日誌:

id is not in products
id is in products

"key" in obj

可能只測試與數組鍵非常不同的對象屬性值





object