Metamétodos aritméticos - Parte 1
Parte de la sección Logic & Flow del Journey de Lua de Coddy — lección 21 de 54.
Has aprendido a personalizar lo que sucede cuando imprimes una tabla usando __tostring. Ahora descubrirás que las metatablas también pueden definir lo que sucede cuando usas operadores aritméticos como + y - en tus tablas.
Normalmente, si intentas sumar dos tablas con el operador +, Lua te dará un error porque no sabe cómo sumar tablas. Pero con los metamétodos aritméticos, puedes definir exactamente qué significa la suma para tus tipos de datos personalizados.
El metamétodo __add controla el comportamiento de la suma. Cuando Lua encuentra el operador + entre dos valores y al menos uno tiene una metatabla con __add, llama a esa función en lugar de producir un error:
local v1 = {x = 3, y = 4}
local v2 = {x = 1, y = 2}
local meta = {
__add = function(a, b)
return {x = a.x + b.x, y = a.y + b.y}
end
}
setmetatable(v1, meta)
setmetatable(v2, meta)
local v3 = v1 + v2
print(v3.x, v3.y) -- Salida: 4 6La función __add recibe dos argumentos: el operando izquierdo y el operando derecho. En este ejemplo, crea una nueva tabla con valores x e y que son la suma de los valores correspondientes de ambas tablas de entrada.
De manera similar, el metamétodo __sub controla la resta con el operador -:
local meta = {
__sub = function(a, b)
return {x = a.x - b.x, y = a.y - b.y}
end
}
setmetatable(v1, meta)
setmetatable(v2, meta)
local v3 = v1 - v2
print(v3.x, v3.y) -- Salida: 2 2Esta capacidad de definir el comportamiento personalizado de los operadores se llama sobrecarga de operadores.
Desafío
FácilEscribe una función addVectors que tome x1, y1, x2 y y2 y devuelva el resultado de sumar dos vectores.
Crea dos tablas de vectores con las coordenadas dadas, adjunta una metatabla con el metamétodo __add para habilitar la suma de vectores, súmalos usando el operador + y devuelve el resultado como una cadena formateada.
Lógica:
- Crea la primera tabla de vector con las claves
x = x1ey = y1 - Crea la segunda tabla de vector con las claves
x = x2ey = y2 - Crea una metatabla con
__addque tome dos vectores y devuelva una nueva tabla conx = a.x + b.xey = a.y + b.y - Adjunta la metatabla a ambas tablas de vectores usando
setmetatable() - Suma los dos vectores usando
v1 + v2 - Devuelve el resultado como una cadena en el formato
"x y"(los valores x e y separados por un espacio)
Parámetros:
x1(número): La coordenada x del primer vectory1(número): La coordenada y del primer vectorx2(número): La coordenada x del segundo vectory2(número): La coordenada y del segundo vector
Devuelve: La suma de los dos vectores como una cadena en el formato "x y" (string)
Hoja de referencia
Las metatablas pueden definir qué sucede cuando usas operadores aritméticos como + y - en tablas. Esto se llama sobrecarga de operadores.
El metamétodo __add controla el comportamiento de la suma con el operador +:
local v1 = {x = 3, y = 4}
local v2 = {x = 1, y = 2}
local meta = {
__add = function(a, b)
return {x = a.x + b.x, y = a.y + b.y}
end
}
setmetatable(v1, meta)
setmetatable(v2, meta)
local v3 = v1 + v2
print(v3.x, v3.y) -- Salida: 4 6La función __add recibe dos argumentos: el operando de la izquierda y el operando de la derecha.
El metamétodo __sub controla la resta con el operador -:
local meta = {
__sub = function(a, b)
return {x = a.x - b.x, y = a.y - b.y}
end
}
setmetatable(v1, meta)
setmetatable(v2, meta)
local v3 = v1 - v2
print(v3.x, v3.y) -- Salida: 2 2Pruébalo tú mismo
function addVectors(x1, y1, x2, y2)
-- Escribe el código aquí
end
Esta lección incluye un breve cuestionario. Empieza la lección para responderlo y registrar tu progreso.
Todas las lecciones de Logic & Flow
1Iteración avanzada de tablas
Iterar con pairs()Iterar con ipairs()pairs() vs. ipairs()Resumen - Ficha de personaje4Introducción a las Metatablas
¿Qué es una Metatabla?setmetatable y getmetatableEl metamétodo __indexEl metamétodo __newindexEl metamétodo __tostringMetamétodos aritméticos - Parte 1Metamétodos aritméticos - Parte 2Resumen - Tablas de solo lectura2Más funciones de la librería table
table.concat()Construcción de tablas y unpack()table.sort()Ordenamiento personalizado con funcionesRepaso - Tabla de puntuaciones altas