There seems to be a change in the way equality metamethods are executed, but I cannot find the documentation in any of the 5.1, 5.2 or 5.3 reference manuals (under the Change in the Language sections under Incompatabilities)
t1a = {}
t1b = {}
t2 = {}
mt1 = { __eq = function( o1, o2 ) return 'whee' end }
mt2 = { __eq = function( o1, o2 ) return 'whee' end }
setmetatable( t1a, mt1 )
setmetatable( t1b, mt1 )
setmetatable( t2, mt2 )
print( t1a == t1b ) --> true
print( t1a == t2 ) --> false
from (http://lua-users.org/wiki/MetatableEvents) and tested to be true on local 5.1.5 implementation
In Lua 5.3 running this actually yields
true
true
Executing from (https://www.lua.org/demo.html)
Is this a bug? Do metamethods for equality no longer have to be the same reference?
I'm not a Lua expert, but comparing the 5.2 docs:
"eq": the == operation. The function getequalhandler defines how Lua chooses a metamethod for equality. A metamethod is selected only when both values being compared have the same type and the same metamethod for the selected operation, and the values are either tables or full userdata.
and the 5.3 docs:
__eq: the equal (==) operation. Behavior similar to the addition operation, except that Lua will try a metamethod only when the values being compared are either both tables or both full userdata and they are not primitively equal. The result of the call is always converted to a boolean.
the 5.3 docs list no requirement that the operands have the same metamethod.
If I'm reading the source code on the Lua website right, this changed between Lua 5.2 and 5.3.
In Lua 5.2, if a pair of tables or userdata are not equal by reference, the equality of the two __eq metamethods was checked in luaV_equalobj_ (using get_equalTM, where TM stands for "tag method", the old name for metamethods), and only then would the metamethod be used. (In 5.1 the process is similar, but the methods are called luaV_equalval and lua_getcompTM.) In 5.3, luaV_equalobj looks for an __eq metamethod in the first operand and then in the second operand; if any metamethod was found, it is called.
There was a discussion about this on the Lua list in 2015: Lua 5.3 changes to .__eq (easier-to-read Nabble version).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With