100% Free Forever
AI-Powered Learning
Industry Expert Content
Certificates & Badges
Learn At Your Own Pace
Ruby

Operator Overloading

Learn how Ruby implements operators as ordinary methods, letting you define custom `+`, `==`, `<<`, and other operators on your own classes for expressive, idiomatic APIs.

Advanced OOPIntermediate9 min readJul 9, 2026
Analogies

Operator Overloading

In Ruby, operators like +, -, ==, <<, and [] are not special syntax handled by the interpreter — they are ordinary method calls with convenient syntactic sugar. Writing a + b is equivalent to writing a.+(b). Because of this, you can define these methods on your own classes to give custom objects natural, expressive behavior, a technique called operator overloading. This lets domain objects like Money, Vector, or Point support arithmetic and comparison the way built-in numeric types do.

🏏

Cricket analogy: When Virat Kohli's bat meets the ball, the umpire doesn't invent a new rule each time — the collision is just a defined action, the same way a + b is really a.+(b) calling a normal method, letting a custom Score class add runs naturally.

Defining arithmetic and comparison operators

To overload an operator, define a method whose name is the operator symbol, accepting one argument (the right-hand operand) for binary operators. Ruby permits overloading most operators except a handful of structural ones like =, .., &&, ||, and not, which remain fixed language constructs.

🏏

Cricket analogy: You can coach a batter to sweep, drive, or cut, but you can't redefine what 'out' fundamentally means; likewise Ruby lets you overload most operator methods but keeps structural ones like = and && fixed language rules.

ruby
class Vector
  attr_reader :x, :y

  def initialize(x, y)
    @x, @y = x, y
  end

  def +(other)
    Vector.new(x + other.x, y + other.y)
  end

  def ==(other)
    other.is_a?(Vector) && x == other.x && y == other.y
  end

  def to_s
    "(#{x}, #{y})"
  end
end

v1 = Vector.new(1, 2)
v2 = Vector.new(3, 4)
puts v1 + v2   #=> (4, 6)
puts v1 == Vector.new(1, 2) #=> true

Unary, indexing, and comparison operators

Unary operators like -@ (negation) and +@ (unary plus) use the @ suffix in their method name to distinguish them from binary versions. Indexing is implemented via [] and []=, and the spaceship operator <=> returns -1, 0, or 1 and is the single method needed to gain full ordering support when combined with the Comparable module.

🏏

Cricket analogy: Distinguishing a batter's forward defensive from an aggressive drive needs a clear label; Ruby uses -@ and +@ suffixes to separate unary negation from addition, and <=> lets a Score class gain full ordering via Comparable.

ruby
class Vector
  # ...
  def -@
    Vector.new(-x, -y)
  end

  def [](index)
    index.zero? ? x : y
  end
end

v = Vector.new(5, -3)
puts(-v)     #=> (-5, 3)
puts v[0]    #=> 5

Python calls this same feature 'dunder methods' (__add__, __eq__, __lt__), and JavaScript has no equivalent — you cannot overload + for custom objects at all in vanilla JS. Ruby's approach is arguably the most direct: the operator literally is the method name, with no special double-underscore naming convention.

Overloading == without also overloading hash and eql? can produce surprising behavior when your objects are used as Hash keys or in a Set, since those data structures rely on hash/eql?, not ==, for lookups. Also, overloading operators to do something unexpected (e.g. making + delete data) violates the principle of least surprise and should be avoided.

  • Ruby operators are syntactic sugar for method calls, e.g. a + b is a.+(b).
  • Define a method named after the operator symbol to overload it on a custom class.
  • Unary operators use an @ suffix in the method name, e.g. -@ for unary minus.
  • [] and []= implement custom indexing behavior.
  • <=> combined with the Comparable module provides full ordering with minimal code.
  • Always keep overloaded operators' behavior intuitive and consistent with their conventional meaning.

Practice what you learned

Was this page helpful?

Topics covered

#Ruby#RubyStudyNotes#Programming#OperatorOverloading#Operator#Overloading#Defining#Arithmetic#StudyNotes#SkillVeris