Javascript 此类型是否可以使用“检查”;“对象”;要改进吗?

Javascript 此类型是否可以使用“检查”;“对象”;要改进吗?,javascript,equals,equality,typeof,type-coercion,Javascript,Equals,Equality,Typeof,Type Coercion,和你的一样吗 if (typeof a !== "object" && typeof b !== "object") { return a == b; } ... // check pairwise equality of object a & b using `for in` 是否有任何b的typeof b==“object”会改变语义 有什么可怕的边缘案例我应该知道吗?比较对象和本机类型,它们具有非直观的布尔相等或非布尔性质?包括浏览器中的任何错误(我是说你

和你的一样吗

if (typeof a !== "object" && typeof b !== "object") {
    return a == b;
}
... // check pairwise equality of object a & b using `for in`
是否有任何
b
typeof b==“object”
会改变语义

有什么可怕的边缘案例我应该知道吗?比较
对象
本机类型
,它们具有非直观的布尔相等或非布尔性质?包括浏览器中的任何错误(我是说你IE6!)

这不一样。
下面是一个例子来了解原因:

if (typeof a !== "object") {
    return a == b;
}
同样的情况也可能发生在数字上:

var a = "a string";
var b = new String("a string");
console.log(typeof a);//"string" !== "object"
console.log(typeof b);//"object" === "object"
console.log('"' + a + '" ' + (a==b?"==":"!=") + ' "' + b + '"');
由于显而易见的原因,您的两个if语句不相同。
您可以通过使用
instanceof
操作员来满足巡更需求,从而“改进”您的类型检查:

var a = 1;
var b = new Number(1);

第二个检查与第一个检查不完全相同,只是因为JavaScript是弱类型的,所以至少要考虑“<代码> toStrug()/<代码>效果”以及其他。例如,第一次检查失败,但第二次检查通过:

if ((typeof a !== "object" || a instanceof Number || a instanceof String) &&
    (typeof b !== "object" || b instanceof Number || b instanceof String))
    return a == b;

或者,稍微简单一点(显示一个你可能想考虑的情况……但是这通过了两个检查):

一种修复方法是使用
==
进行值和类型检查,您还可以进行类型检查……但我不完全确定您的目的是什么,因为当前检查显然是“非对象”。

请从中查看。它“在两个对象之间执行优化的深度比较,以确定它们是否应该被视为相等。”它适用于所有类型的变量。这就是它的实现方式:

var a = 0;
var b = "0";
请参阅以查看此函数使用的其他函数


很容易忽略一些边缘情况,因此我建议使用经过良好测试的代码,如本例,而不是重新设计轮子。

这取决于您关心的内容,例如
var a=“[object]”
var b={}
在第二次检查中相等,但在第一次检查中不相等。@NickCraver-yikes!这是一个可怕的副作用!基本上,我担心对象与这些东西相等。@Nick:在回答中写下这一点,因为它是:“[object object]”=={},回答这一行:
b
是否有
typeof b====“object”
哪一个会改变语义?记住javascript具有自动类型转换功能-如果需要,可以通过执行
a===b
来解决这个问题wanted@MartinJespersen我知道我在做什么类型强制(部分)只是想找到像上面一样可怕的边缘案例。cmon Nick。至少让我相信我知道类型强制是如何工作的,以及
==
===
之间的区别。)@雷诺斯-记住,所有的答案都会被很多人看到,实际上很少是我的答案都是索利的作品,请不要生气:)我知道,只是觉得有点高人一等。很好。每个人都需要记住类型胁迫的恐怖。尤其是因为边缘情况不直观。@Raynos:如果您只想检查简单类型,只需检查a&b;上是否存在prototype属性即可。)
如果(!a.prototype&&!b.prototype){returna==b;}
@MartinJespersen我确实想从CommonJS实现,这有点“错误”。@Raynos:在这种情况下,不要吝啬于检查。。。对每件事都做些分类,不要在任何时候进行分类all@MartinJespersen规范说,诉诸类型强制:)比你早得多。我从该源获取了大部分函数:)。可耻的是,它不满足CommonJS规范。
var a = 0;
var b = "0";
  // Perform a deep comparison to check if two objects are equal.
  _.isEqual = function(a, b) {
    // Check object identity.
    if (a === b) return true;
    // Different types?
    var atype = typeof(a), btype = typeof(b);
    if (atype != btype) return false;
    // Basic equality test (watch out for coercions).
    if (a == b) return true;
    // One is falsy and the other truthy.
    if ((!a && b) || (a && !b)) return false;
    // Unwrap any wrapped objects.
    if (a._chain) a = a._wrapped;
    if (b._chain) b = b._wrapped;
    // One of them implements an isEqual()?
    if (a.isEqual) return a.isEqual(b);
    // Check dates' integer values.
    if (_.isDate(a) && _.isDate(b)) return a.getTime() === b.getTime();
    // Both are NaN?
    if (_.isNaN(a) && _.isNaN(b)) return false;
    // Compare regular expressions.
    if (_.isRegExp(a) && _.isRegExp(b))
      return a.source     === b.source &&
             a.global     === b.global &&
             a.ignoreCase === b.ignoreCase &&
             a.multiline  === b.multiline;
    // If a is not an object by this point, we can't handle it.
    if (atype !== 'object') return false;
    // Check for different array lengths before comparing contents.
    if (a.length && (a.length !== b.length)) return false;
    // Nothing else worked, deep compare the contents.
    var aKeys = _.keys(a), bKeys = _.keys(b);
    // Different object sizes?
    if (aKeys.length != bKeys.length) return false;
    // Recursive comparison of contents.
    for (var key in a) if (!(key in b) || !_.isEqual(a[key], b[key])) return false;
    return true;
  };