Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Don’t fail when comparing +0 and -0 #223

Closed
davidaurelio opened this Issue · 8 comments

5 participants

@davidaurelio

I’d like to know whether failing equality tests for positive and negative zero solved some real world problems.

In my case it just lead to a very long debugging session, since mocha’s diff wasn’t showing anything for two compared 2d-matrices (arrays of six numbers).

I’d argue that for most, if not all, mathematical cases the distinction between positive and negative zero is irrelevant. It’s an implementation detail of IEEE 754 floating point numbers, and did more harm than good for my personal case.

I’ve tried to find any issues referencing this distinction, but only found the change log mentioning this. If there aren’t very good reasons to have this behavior, please change it back.

@domenic
Owner

I'm a bit surprised that you didn't open this bug on Mocha's diff viewer.

The issue is that they are different values, and when testing for when two values are equal in JavaScript, the spec says to treat them differently. If you want loose equality, use .eql or .deep.equal.

@davidaurelio

Thank you for the reply.

If you want loose equality, use .eql or .deep.equal.

I am using .deep.equal since I am comparing arrays. A quick check reveals:

expect(0).equal(-0); // does not throw
expect(0).eql(-0); // throws 
expect([0]).eql([-0]); // throws 

It seems to me that I’m not the only one who is confused.

The issue is that they are different values, and when testing for when two values are equal in JavaScript, the spec says to treat them differently.

@domenic, I am sure that you know the ES spec very well, but let me add some context:

chai’s docs state that

.equal(value) […] Asserts that the target is strictly equal (===) to value. Alternately, if the deep flag is set, asserts that the target is deeply equal to value. […] .eql(value) […] Asserts that the target is deeply equal to value.

I cannot find any reference to the SameValue algorithm here. What I see is the strict equality operator, which uses Strict Equality Comparison. “This algorithm differs from the SameValue Algorithm (7.2.3) in its treatment of signed zeroes and NaNs.”

Apart from that, the major part of appliances of SameValue in the specs relate to property definition/access (with strings) and prototype lookups. The only “equality test” that uses it is Object.is. Other new ES6 methods in Sets and Maps use the SameValueZero algorithm that does not distinguish between +0 and -0.

I asked about the problems that this comparison solved in chai because I am sure that from time to time somebody actually wants to distinguish between signed zeros. Maybe a .sameValue() method would be the right place for this type of comparison.

Besides spec internals I think that the current behaviour is unexpected and confusing and lets tests of mathematical calculations fail in unexpected ways. I see the value of not failing the claimed strict equality test (===) for NaN. That’s pragmatic. I wanted to know whether failing for +0 and -0 was pragmatic, because I don’t have that impression.

I'm a bit surprised that you didn't open this bug on Mocha's diff viewer.

I’ve thought about doing that. If I would test for SameValue I would regard this as a mocha issue and file a ticket there. But I don’t.

I’m not calling this a bug in chai, since it is a design decision. I just think it does not help and adds confusion, and therefore ask to remove this behaviour again.

@skeggse

At the very least, it seems like this should be documented (in the documentation, not the issues).

@skeggse skeggse referenced this issue in mochajs/mocha
Closed

Diff Viewer Verbosity with -0 #1229

@Lexicality

@skeggse This isn't Mocha's fault - Chai throws AssertionError: expected [ 0 ] to deeply equal [ 0 ] without any further information. It took me an hour of debugigng until I remembered -0 was a thing.
There really needs to be some kind of note in the documentation - and some method of comparing structures that avoids this "feature". I had to throw a bunch of Math.abs into my code just to get the tests to work.

@keithamus
Owner

I'm closing this, as #298 covers @Lexicality's points - Chai will now explicitly tell you that expected [ -0 ] to deeply equal [ 0 ]. As such anyone bitten by this will notice pretty quickly.

If anyone doesn't like that this has been closed, please speak up - or raise a new issue.

@keithamus keithamus closed this
@skeggse

LGTM

@davidaurelio

I still don’t think this behaviour is more useful than treating +0 and -0 as equal, simply because the difference between the two values hardly matters in most cases. Quite the contrary.

At least it’s documented now.

@domenic
Owner

I think it matters in a testing framework that is trying to help you find potential subtle bugs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.