Jasmine JavaScript 测试 - toBe vs toEqual

2022-01-11 00:00:00 jasmine javascript

假设我有以下内容:

var myNumber = 5;期望(myNumber).toBe(5);期望(myNumber).toEqual(5);

以上两个测试都将通过.toBe()toEqual() 在计算数字时有区别吗?如果是这样,我什么时候应该使用一个而不是另一个?

解决方案

对于原始类型(例如数字、布尔值、字符串等),toBetoEqual没有区别;任何一个都适用于 5true"the cake is a lie".

为了理解 toBetoEqual 之间的区别,让我们想象三个对象.

var a = { bar: 'baz' },b = { foo: a },c = { foo: a };

使用严格比较(===),有些东西是相同的":

<代码>>b.foo.bar === c.foo.bar真的>b.foo.bar === a.bar真的>c.foo === b.foo真的

但是有些东西,即使它们相等",也不是相同的",因为它们代表了存在于内存中不同位置的对象.

<代码>>b === c错误的

Jasmine 的 toBe 匹配器只不过是严格相等比较的包装器

expect(c.foo).toBe(b.foo)

是一样的

expect(c.foo === b.foo).toBe(true)

不要只相信我的话;参见toBe的源代码.p>

但是bc代表功能上等价的对象;他们都长得像

{ foo: { bar: 'baz' } }

如果我们可以说 bc 是相等的",那不是很好吗?即使它们不代表同一个对象?

输入 toEqual,它检查深度相等";(即对对象进行递归搜索以确定其键的值是否相等).以下两项测试都将通过:

expect(b).not.toBe(c);期望(b).toEqual(c);

希望这有助于澄清一些事情.

Let's say I have the following:

var myNumber = 5;
expect(myNumber).toBe(5);
expect(myNumber).toEqual(5);

Both of the above tests will pass. Is there a difference between toBe() and toEqual() when it comes to evaluating numbers? If so, when I should use one and not the other?

解决方案

For primitive types (e.g. numbers, booleans, strings, etc.), there is no difference between toBe and toEqual; either one will work for 5, true, or "the cake is a lie".

To understand the difference between toBe and toEqual, let's imagine three objects.

var a = { bar: 'baz' },
    b = { foo: a },
    c = { foo: a };

Using a strict comparison (===), some things are "the same":

> b.foo.bar === c.foo.bar
true

> b.foo.bar === a.bar
true

> c.foo === b.foo
true

But some things, even though they are "equal", are not "the same", since they represent objects that live in different locations in memory.

> b === c
false

Jasmine's toBe matcher is nothing more than a wrapper for a strict equality comparison

expect(c.foo).toBe(b.foo)

is the same thing as

expect(c.foo === b.foo).toBe(true)

Don't just take my word for it; see the source code for toBe.

But b and c represent functionally equivalent objects; they both look like

{ foo: { bar: 'baz' } }

Wouldn't it be great if we could say that b and c are "equal" even if they don't represent the same object?

Enter toEqual, which checks "deep equality" (i.e. does a recursive search through the objects to determine whether the values for their keys are equivalent). Both of the following tests will pass:

expect(b).not.toBe(c);
expect(b).toEqual(c);

Hope that helps clarify some things.

相关文章