record Person(String name, int age) {}
if (obj instanceof Person person) {
System.out.println("Name: " + person.name());
}
Now let’s consider a more traditional example. Geometric shapes are a classic way to demonstrate how sealed interfaces work with records, and they make pattern matching especially clear. The elegance of this combination is evident in switch expressions (introduced in Java 17), which let you write concise, type‑safe code that resembles algebraic data types in functional languages:
sealed interface Shape permits Rectangle, Circle, Triangle {}
record Rectangle(double width, double height) implements Shape {}
record Circle(double radius) implements Shape {}
record Triangle(double base, double height) implements Shape {}
public class RecordPatternMatchingExample {
public static void main(String[] args) {
Shape shape = new Circle(5);
// Expressive, type-safe pattern matching
double area = switch (shape) {
case Rectangle r -> r.width() * r.height();
case Circle c -> Math.PI * c.radius() * c.radius();
case Triangle t -> t.base() * t.height() / 2;
};
System.out.println("Area = " + area);
}
}
Here, the Shape
type is a sealed interface, permitting only Rectangle
, Circle
, and Triangle
. Because this set is closed, the switch is exhaustive and requires no default branch.
Using records as data transfer objects
Records excel as data transfer objects (DTOs) in modern API designs such as REST, GraphQL, gRPC, or inter‑service communication. Their concise syntax and built‑in equality make records ideal for mapping between service layers. Here’s an example: