BudiBadu Logo
Samplebadu

Scala by Example: Case Classes

Scala 3

Modeling immutable data structures with this sample code demonstrating case class auto-generated methods, instantiation without new keyword, structural equality comparison, copy method for creating modified instances, built-in toString implementation, and seamless pattern matching support.

Code

// Define a case class
case class Point(x: Int, y: Int)

// Instantiation (no 'new' needed)
val p1 = Point(1, 2)
val p2 = Point(1, 2)
val p3 = Point(3, 4)

// Equality check (by value, not reference)
println(p1 == p2) // true

// Copying with modification
val p4 = p1.copy(y = 5) // Point(1, 5)

// Built-in toString
println(p4) // "Point(1,5)"

// Pattern matching support
p1 match {
  case Point(0, 0) => println("Origin")
  case Point(x, y) => println(s"At $x, $y")
}

Explanation

Case classes are specialized classes optimized for modeling immutable data, and they're one of Scala's most beloved features. When you define a class as a case class, the compiler automatically generates substantial boilerplate code including:

  • An apply method in the companion object for instantiation without new
  • An unapply method enabling pattern matching and deconstruction
  • equals and hashCode methods implementing structural equality
  • A toString method providing meaningful string representation
  • A copy method for creating modified copies while maintaining immutability

Structural equality is one of the most important features of case classes. Two case class instances are considered equal if all their fields are equal, unlike regular classes which compare object references by default. This makes case classes ideal for value objects, data transfer objects, and any scenario where you care about the data content rather than object identity. The generated hashCode method ensures case class instances work correctly in hash-based collections like HashMap and HashSet.

The copy method allows you to create a new instance based on an existing one with some fields modified, which is essential for working with immutable data structures. Instead of mutating an object, you create a modified copy. Case classes are designed to work seamlessly with pattern matching, allowing you to deconstruct them easily and extract their fields in match expressions, making them perfect for algebraic data types and domain modeling.

Code Breakdown

2
case class Point(...) automatically generates val fields and utility methods.
10
p1 == p2 compares by value (structural equality), not reference.
13
p1.copy(y = 5) creates new Point keeping x from p1 but changing y.
21
case Point(x, y) deconstructs case class extracting fields for pattern matching.