Difference Between ==, eql?, equal? in ruby

Equality operators: == and !=

The == operator, also known as equality or double equal, will return true if both objects are equal and false if they are not.

str1 = ?This is string?

str2 = ?This is string?

str1 == str2 #Output: => truestr1 != str2 #Output: => false

When comparing numbers of different types (e.g., integer and float), if their numeric value is the same, == will return true.

2 == 2.0 # Output: => true

eql?

The eql? method returns true if obj and other refer to the same hash key. This is used by Hash to test members for equality. For objects of class Object, eql? is synonymous with ==. Subclasses normally continue this tradition by aliasing eql? to their overridden ==method, but there are exceptions. Numeric types, for example, perform type conversion across ==, but not across eql?, so:

1 == 1.0 #=> true1.eql? 1.0 #=> false

equal?

Unlike the == operator which tests if both operands are equal, the equal method checks if the two operands refer to the same object. This is the strictest form of equality in Ruby.

Example: a = ?xyz? and b = ?xyz?

a.object_id # Output: => 20139460b.object_id # Output :=> 19972120a.equal? b # Output: => false

In the example above, we have two strings with the same value. However, they are two distinct objects, with different object IDs. Hence, the equal? method will return false.

Let?s try again, only this time b will be a reference to a. Notice that the object ID is the same for both variables, as they point to the same object.

a = “string”b = aa.object_id # Output: => 18637360b.object_id # Output: => 18637360a.equal? b # Output: => true

Case equality operator: ===

Many of Ruby?s built-in classes, such as String, Range, and Regexp, provide their own implementations of the === operator, also known as case-equality, triple equals or threequals. Because it?s implemented differently in each class, it will behave differently depending on the type of object it was called on. Generally, it returns true if the object on the right ?belongs to? or ?is a member of? the object on the left. For instance, it can be used to test if an object is an instance of a class (or one of its subclasses).

String === “zen” # Output: => trueRange === (1..2) # Output: => trueArray === [1,2,3] # Output: => trueInteger === 2 # Output: => true

Range Implementation of ===

When the === operator is called on a range object, it returns true if the value on the right falls within the range on the left.

(1..4) === 3 # Output: => true(1..4) === 2.345 # Output: => true(1..4) === 6 # Output: => false(“a”..”d”) === “c” # Output: => true(“a”..”d”) === “e” # Output: => false

Implicit usage of the === operator on case/when statements

This operator is also used under the hood on case/when statements. That is its most common use.

minutes = 15case minutes when 10..20 puts “match” else puts “no match”end# Output: match

In the example above, if Ruby had implicitly used the double equal operator (==), the range 10..20 would not be considered equal to an integer such as 15. They match because the triple equal operator (===) is implicitly used in all case/when statements. The code in the example above is equivalent to:

minutes = 15if (10..20) === minutes puts “match”else puts “no match”end# Output: match

21