Javascript中的object相称

原文出处:Object Equality in JavaScript

相称是JavaScript中早先最让人疑心的部份。=====的比较、强迫范例的递次等等,都使得这个题目变得复杂。本日,我们会聚焦另一个方面:object相称是怎样完成的。

你或许以为,假如两个object有雷同的属性而且它们多有的属性值都雷同,那末这两个object应该是相称的。我们来看看是不是如我们所料:

var jangoFett = {
    occupation: "Bounty Hunter",
    genetics: "superb"
};

var bobaFett = {
    occupation: "Bounty Hunter",
    genetics: "superb"
};

// Outputs: false
console.log(bobaFett === jangoFett);

bobaFettjangoFett的属性完全雷同,然则两个object并不以为是相称的。岂非是我们运用恒等运算符的缘由?我们来考证下:

// Outputs: false
console.log(bobaFett == jangoFett);

我们如许做,是因为JavaScript内部其实有两套差别的计划来考证相称(译者加:ecma范例中定义的[The Strict Equality Comparison Algorithm
](http://www.ecma-international…)。像字符串以及数值这类基础范例是依据它们的值举行比较的;但像数组、日期以及简朴对象这类object是依据它们的援用举行推断的。依据援用的推断会搜检所给的object是不是指向内存中的雷同地点。下面这个例子会论述JavaScript中相称运算符的完成道理:

var jangoFett = {
    occupation: "Bounty Hunter",
    genetics: "superb"
};

var bobaFett = {
    occupation: "Bounty Hunter",
    genetics: "superb"
};

var callMeJango = jangoFett;

// Outputs: false
console.log(bobaFett === jangoFett);

// Outputs: true
console.log(callMeJango === jangoFett);

一方面讲,jangoFettbobaFett这两个变量援用自两个具有完全雷同属性的object,但确实为两个差别的实例;另一方面,jangoFettcallMeJango指向雷同的实例。

因而,当你想要考证对象相称时,你须要清晰你是想要怎样的相称。假如你是想考证两个实例是不是完完全全雷同,你可以运用JavaScript内置的相称运算符;抑或你是想考证两个实例具有“雷同的值”,如许的话,你可以须要多做些事情。

以下是磨练object“值相称”的一种基础完成:

function isEquivalent(a, b) {
    // Create arrays of property names
    var aProps = Object.getOwnPropertyNames(a);
    var bProps = Object.getOwnPropertyNames(b);

    // If number of properties is different,
    // objects are not equivalent
    if (aProps.length != bProps.length) {
        return false;
    }

    for (var i = 0; i < aProps.length; i++) {
        var propName = aProps[i];

        // If values of same property are not equal,
        // objects are not equivalent
        if (a[propName] !== b[propName]) {
            return false;
        }
    }

    // If we made it this far, objects
    // are considered equivalent
    return true;
}

// Outputs: true
console.log(isEquivalent(bobaFett, jangoFett));

如你所见,想要考证object实例“值相称”,我们必需去遍历object中每一个属性,看其是不是相称。假如我们把上面完成的这个简朴计划应用在我们的例子中,许多状况都是还没有处置惩罚的。比方:

  • 假如某个属性是一个object
  • 假如某个属性值时NaN(JavaScript中唯一一个本身不相称本身的值)
  • 假如a有个属性的值为undefined,而b中没有这个属性(因而都等同于undefined

想要一个磨练object实例“值相称”的硬朗的要领,最好是运用一个涵盖种种边境状况的、经由周全测试的库。UnderscoreLo-Dash这两个库中的_.isEqual要领对处置惩罚object深度比较举行了很好的完成。你可以如许运用它们:

// Outputs: true
console.log(_.isEqual(bobaFett, jangoFett));

愿望这个JavaScript的小知识点可以协助你更好地明白object实例相称的完成道理。

    原文作者:loosenqian
    原文地址: https://segmentfault.com/a/1190000018367194
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞