En Dart, la sobrecarga de operadores permite redefinir el comportamiento de operadores como +
, -
, *
, entre otros, para adaptarlos a clases personalizadas. Esto es útil cuando tienes clases que representan estructuras de datos complejas, como vectores o matrices, y deseas realizar operaciones matemáticas o lógicas directamente entre instancias de estas clases de forma natural y legible.
La sobrecarga de operadores permite que una clase en Dart defina su propio comportamiento para ciertos operadores. Dart soporta sobrecarga de operadores a través de métodos especiales, como operator +
, operator -
, operator ==
, y otros. Al implementar estos métodos en una clase, puedes modificar cómo responde a los operadores comunes al interactuar con instancias de esa clase.
Para sobrecargar un operador, declara un método utilizando la palabra clave operator
seguida del símbolo del operador. Por ejemplo:
class Punto {
final int x, y;
Punto(this.x, this.y);
// Sobrecarga del operador +
Punto operator +(Punto otro) {
return Punto(x + otro.x, y + otro.y);
}
}
void main() {
Punto p1 = Punto(2, 3);
Punto p2 = Punto(4, 5);
Punto resultado = p1 + p2;
print("Resultado: (${resultado.x}, ${resultado.y})"); // Imprime: (6, 8)
}
En este ejemplo, el operador +
se sobrecarga para sumar las coordenadas de dos instancias de Punto
.
*
Aquí sobrecargamos el operador *
para multiplicar las coordenadas de un punto por un escalar.
class Punto {
final int x, y;
Punto(this.x, this.y);
Punto operator *(int escalar) {
return Punto(x * escalar, y * escalar);
}
}
void main() {
Punto p1 = Punto(3, 4);
Punto resultado = p1 * 3;
print("Resultado: (${resultado.x}, ${resultado.y})"); // Imprime: (9, 12)
}
==
y hashCode
Si sobrecargas el operador ==
, también es recomendable redefinir hashCode
para mantener consistencia en comparaciones de igualdad.
class Punto {
final int x, y;
Punto(this.x, this.y);
bool operator ==(Object otro) {
if (identical(this, otro)) return true;
return otro is Punto && otro.x == x && otro.y == y;
}
int get hashCode => Object.hash(x, y);
}
void main() {
Punto p1 = Punto(2, 3);
Punto p2 = Punto(2, 3);
print(p1 == p2); // Imprime: true
}
En este ejemplo, el operador ==
se redefine para comparar los valores de x
e y
en lugar de comparar las referencias de objetos.
[]
para acceder a elementos
Puedes sobrecargar el operador []
para crear clases que actúen como listas o mapas.
class Vector {
List<int> _elementos;
Vector(this._elementos);
int operator [](int indice) => _elementos[indice];
void operator []=(int indice, int valor) {
_elementos[indice] = valor;
}
}
void main() {
Vector vector = Vector([10, 20, 30]);
print(vector[1]); // Imprime: 20
vector[1] = 50;
print(vector[1]); // Imprime: 50
}
-
Este ejemplo muestra cómo sobrecargar el operador -
para restar las coordenadas de dos puntos.
class Punto {
final int x, y;
Punto(this.x, this.y);
Punto operator -(Punto otro) {
return Punto(x - otro.x, y - otro.y);
}
}
void main() {
Punto p1 = Punto(10, 5);
Punto p2 = Punto(4, 3);
Punto resultado = p1 - p2;
print("Resultado: (${resultado.x}, ${resultado.y})"); // Imprime: (6, 2)
}
Dart permite la sobrecarga de varios operadores, entre ellos:
+
, -
, *
, /
, ~/
, %
==
, <
, >
, <=
, >=
[]
, []=
&
, |
, ^
, ~
, <<
, >>
++
, --
Para más información sobre la sobrecarga de operadores, consulta la documentación oficial de Dart.
Jorge García
Fullstack developer