0

For example, in Javascript [1,2,3] === [1,2,3] and [1,2,3] == [1,2,3] are both false. Even the simpler case of the empty array is also false. The reason being that arrays are reference types and [1,2,3] and [1,2,3] are different as references. Javascript is not unique in this regard and pretty much every language implements equality as being reference equality except for the most basic types like integers and maybe some built-in types.

Why is this the case? What's so hard about making the default equality operator something stronger? So instead of just comparing references why is it so hard to compare structural properties as well?

I know that many languages provide facilities for overloading certain operators to mean something else so that == will mean what you want it to mean instead of the usual weak reference equality. My question is not whether the language provides such facilities but why the default equality operator isn't something more sensible so that [1,2,3] == [1,2,3] evaluates to true by default and requires no programmer intervention.

In python the above example evaluates to true but if you define the following class

class A:
  def __init__(self, prop):
    self.prop = prop

and then compare a = A(1) to b = A(1) then the answer will be false even though structurally a and b are the same and there is no way to tell them apart if all you know is the bit pattern that defines the object.

David K.
  • 6,153
  • 10
  • 47
  • 78
  • Why is the assumption that it's hard to do just because they decided to implement it the way they did? – kinakuta May 31 '12 at 03:48
  • @kinakuta because almost every language out there does it that way which indicates some kind of barrier. If it was easy somebody out there would have implemented a language that does the obvious thing for array equality and more general types as well. – David K. May 31 '12 at 03:49

3 Answers3

2

Not all languages do this. C++ uses == on objects to mean equality (though == on pointers does mean reference equality). I believe (though I'm not fully sure) that the D programming language reserves == for value equality and the is operator for reference equality.

I think this is just a design decision for JavaScript and a few other languages. There is no reason that it has to be this way.

templatetypedef
  • 362,284
  • 104
  • 897
  • 1,065
2

Not all languages work the way you describe. For example, in Python == is equality and is is reference comparison:

>>> a = [1,2,3]
>>> b = [1,2,3]
>>> a == b
True
>>> a is b
False
Greg Hewgill
  • 951,095
  • 183
  • 1,149
  • 1,285
  • That is true but if I define my own custom class with its own properties then `a = Klass(val)` will not be equal to `b = Klass(val)`. – David K. May 31 '12 at 04:00
  • @davidk01: You need to implement the [`__eq__` method](http://docs.python.org/reference/datamodel.html#object.__eq__) for your class. That is what is called by `==`. – Greg Hewgill May 31 '12 at 04:01
  • Yes. That's my point. What's so hard about having a default `__eq__` operator that does the right thing. – David K. May 31 '12 at 04:04
  • Ok, I don't understand your point then. In Python, `==` *does* do the "right thing" for Python's built-in object types, including arrays. If you implement your own class, then you are responsible for defining what `==` means, if that matters to you. – Greg Hewgill May 31 '12 at 04:05
  • I've amended my answer to be more clear about exactly what I'm asking. The obvious thing to do when comparing objects is too look at all the properties and verify that they are same on both sides of the equality operator. Only when the programmer wants to use some other form of equality should he have to define it. If I was doing modular arithmetic then it might make sense to have `1 == 6` and in that case I should redefine equality. You don't expect a language to leave it up to you to say whether `1 == 6` is true or false so why isn't this applicable to custom types as well? – David K. May 31 '12 at 04:09
  • @davidk01: “You don't expect a language to leave it up to you to say whether `1 == 6` is true or false”. Right, you leave it up to whoever designs the `int` type to say how it behaves. That's pretty much what designing a type is. So custom types aren't special in that regard. – bignose Jan 31 '16 at 10:45
0

pretty much every language implements equality as being reference equality

As indicated by the types tag on this question, many languages implement equality as a behaviour of the type. This makes sense: most types will have some properties that can change on an instance without the semantic “value” of that instance changing.

So the answer I'd give is: equality is not hard, it is up to the type to define what instances are equal. Any defaults in the absence of such an explicit decision should be conservative.

If you're creating a custom type, that makes it your responsibility to decide; if the language supports inheritance, use that to express your decision that “equality should behave like this other more basic type”. Otherwise, code the equality test explicitly for the type, just as is done for the existing types you believe have the correct behaviour.

bignose
  • 30,281
  • 14
  • 77
  • 110