Sorting Arrays of Abstract Class Extenders in JavaScript
Sorting arrays is a fundamental task in programming. However, when dealing with arrays containing objects that extend an abstract class, the sorting process can become more complex. This article will guide you through the best practices for sorting such arrays in JavaScript.
The Problem: Abstract Classes and Sorting
Imagine you have an abstract class Shape
with properties like area
and perimeter
. You then create concrete classes like Circle
, Square
, and Triangle
that extend Shape
and implement specific area and perimeter calculations.
Now, let's say you have an array containing instances of these classes:
class Shape {
constructor(name) {
this.name = name;
}
getArea() {
throw new Error("Abstract method: getArea must be implemented.");
}
getPerimeter() {
throw new Error("Abstract method: getPerimeter must be implemented.");
}
}
class Circle extends Shape {
constructor(radius, name) {
super(name);
this.radius = radius;
}
getArea() {
return Math.PI * this.radius * this.radius;
}
getPerimeter() {
return 2 * Math.PI * this.radius;
}
}
class Square extends Shape {
constructor(side, name) {
super(name);
this.side = side;
}
getArea() {
return this.side * this.side;
}
getPerimeter() {
return 4 * this.side;
}
}
const shapes = [
new Circle(5, "Circle 1"),
new Square(3, "Square 1"),
new Circle(2, "Circle 2"),
];
You want to sort this shapes
array based on the area of each shape. How can you use Array.sort
effectively with this structure?
The Solution: Custom Sorting Functions
JavaScript's Array.sort
method accepts a comparison function that determines the order of elements. Here's how you can apply this to sort your array of shapes:
shapes.sort((a, b) => {
return a.getArea() - b.getArea();
});
In this example, we define a comparison function that compares the getArea()
results of two shapes (a
and b
). If a
's area is larger than b
's, the function returns a positive number, placing a
after b
in the sorted array. If a
's area is smaller, the function returns a negative number, placing a
before b
.
Key Points to Remember
- Polymorphism: By using the
getArea()
method from the abstract class, the comparison function handles all concrete classes without needing to know their specific type. This demonstrates the power of polymorphism. - Comparison Function: The comparison function should return a negative number if
a
should come beforeb
, a positive number ifa
should come afterb
, and zero if they are considered equal. - Immutability:
Array.sort
modifies the original array in place. If you need to preserve the original array, create a copy before sorting.
Beyond Area: Custom Sorting Criteria
The approach outlined above can be extended to sort your shapes based on any criteria. For example, to sort based on perimeter, you would modify the comparison function like this:
shapes.sort((a, b) => {
return a.getPerimeter() - b.getPerimeter();
});
Conclusion
Sorting arrays containing objects that extend an abstract class is a common challenge in object-oriented programming. JavaScript's Array.sort
method provides a powerful mechanism for accomplishing this. By defining custom comparison functions that leverage polymorphism, you can easily sort based on any desired criteria.
Remember to always test your sorting logic thoroughly to ensure it produces the expected results and consider creating copies if you need to preserve the original array.