Add __unm and __len metatags.
This commit is contained in:
@@ -26,8 +26,6 @@ import org.luaj.vm2.lib.DebugLib;
|
|||||||
public class LuaClosure extends LuaFunction {
|
public class LuaClosure extends LuaFunction {
|
||||||
private static final UpValue[] NOUPVALUES = new UpValue[0];
|
private static final UpValue[] NOUPVALUES = new UpValue[0];
|
||||||
|
|
||||||
public LuaValue s_metatable;
|
|
||||||
|
|
||||||
public final Prototype p;
|
public final Prototype p;
|
||||||
public final UpValue[] upValues;
|
public final UpValue[] upValues;
|
||||||
|
|
||||||
|
|||||||
@@ -109,7 +109,7 @@ public class LuaString extends LuaValue {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unary operators
|
// unary operators
|
||||||
public LuaValue neg() { return valueOf(-checkarith()); }
|
public LuaValue neg() { double d = scannumber(10); return Double.isNaN(d)? super.neg(): valueOf(-d); }
|
||||||
|
|
||||||
// basic binary arithmetic
|
// basic binary arithmetic
|
||||||
public LuaValue add( LuaValue rhs ) { double d = scannumber(10); return Double.isNaN(d)? arithmt(ADD,rhs): rhs.add(d); }
|
public LuaValue add( LuaValue rhs ) { double d = scannumber(10); return Double.isNaN(d)? arithmt(ADD,rhs): rhs.add(d); }
|
||||||
|
|||||||
@@ -72,6 +72,8 @@ public class LuaValue extends Varargs {
|
|||||||
public static final LuaString MUL = valueOf("__mul");
|
public static final LuaString MUL = valueOf("__mul");
|
||||||
public static final LuaString POW = valueOf("__pow");
|
public static final LuaString POW = valueOf("__pow");
|
||||||
public static final LuaString MOD = valueOf("__mod");
|
public static final LuaString MOD = valueOf("__mod");
|
||||||
|
public static final LuaString UNM = valueOf("__unm");
|
||||||
|
public static final LuaString LEN = valueOf("__len");
|
||||||
public static final LuaString EMPTYSTRING = valueOf("");
|
public static final LuaString EMPTYSTRING = valueOf("");
|
||||||
|
|
||||||
private static int MAXSTACK = 250;
|
private static int MAXSTACK = 250;
|
||||||
@@ -247,9 +249,9 @@ public class LuaValue extends Varargs {
|
|||||||
|
|
||||||
// unary operators
|
// unary operators
|
||||||
public LuaValue not() { return FALSE; }
|
public LuaValue not() { return FALSE; }
|
||||||
public LuaValue neg() { return aritherror("neg"); }
|
public LuaValue neg() { return checkmetatag(UNM, "attempt to perform arithmetic on ").call(this); }
|
||||||
public LuaValue len() { return lenerror(); }
|
public LuaValue len() { return checkmetatag(LEN, "attempt to get length of ").call(this); }
|
||||||
public int length() { error("attempt to get length of "+typename()); return 0; }
|
public int length() { return len().toint(); }
|
||||||
public LuaValue getn() { return typerror("getn"); }
|
public LuaValue getn() { return typerror("getn"); }
|
||||||
|
|
||||||
// object equality, used for key comparison
|
// object equality, used for key comparison
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ local anumber = 111
|
|||||||
local aboolean = false
|
local aboolean = false
|
||||||
local afunction = function() end
|
local afunction = function() end
|
||||||
local athread = coroutine.create( afunction )
|
local athread = coroutine.create( afunction )
|
||||||
local values = { athread, aboolean, afunction, athread }
|
local values = { anumber, aboolean, afunction, athread }
|
||||||
for i=1,#values do
|
for i=1,#values do
|
||||||
print( debug.getmetatable( values[i] ) )
|
print( debug.getmetatable( values[i] ) )
|
||||||
end
|
end
|
||||||
@@ -13,7 +13,14 @@ tostring = function(o)
|
|||||||
return (t=='thread' or t=='function') and t or ts(o)
|
return (t=='thread' or t=='function') and t or ts(o)
|
||||||
end
|
end
|
||||||
|
|
||||||
local buildbin = function(name)
|
local buildunop = function(name)
|
||||||
|
return function(a)
|
||||||
|
print( 'mt.__'..name..'()', type(a), a )
|
||||||
|
return '__'..name..'-result'
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
local buildbinop = function(name)
|
||||||
return function(a,b)
|
return function(a,b)
|
||||||
print( 'mt.__'..name..'()', type(a), type(b), a, b )
|
print( 'mt.__'..name..'()', type(a), type(b), a, b )
|
||||||
return '__'..name..'-result'
|
return '__'..name..'-result'
|
||||||
@@ -25,12 +32,14 @@ local mt = {
|
|||||||
print( 'mt.__call()', type(a), type(b), type(c), b, c )
|
print( 'mt.__call()', type(a), type(b), type(c), b, c )
|
||||||
return '__call-result'
|
return '__call-result'
|
||||||
end,
|
end,
|
||||||
__add=buildbin('add'),
|
__add=buildbinop('add'),
|
||||||
__sub=buildbin('sub'),
|
__sub=buildbinop('sub'),
|
||||||
__mul=buildbin('mul'),
|
__mul=buildbinop('mul'),
|
||||||
__div=buildbin('div'),
|
__div=buildbinop('div'),
|
||||||
__pow=buildbin('pow'),
|
__pow=buildbinop('pow'),
|
||||||
__mod=buildbin('mod'),
|
__mod=buildbinop('mod'),
|
||||||
|
__unm=buildunop('unm'),
|
||||||
|
__len=buildunop('neg'),
|
||||||
}
|
}
|
||||||
|
|
||||||
-- pcall a function and check for a pattern in the error string
|
-- pcall a function and check for a pattern in the error string
|
||||||
@@ -80,10 +89,22 @@ for i=1,#groups do
|
|||||||
print( debug.setmetatable( a, nil ) )
|
print( debug.setmetatable( a, nil ) )
|
||||||
end
|
end
|
||||||
|
|
||||||
|
print( '---- __len' )
|
||||||
|
values = { aboolean, afunction, athread }
|
||||||
print( '---- final metatables' )
|
|
||||||
for i=1,#values do
|
for i=1,#values do
|
||||||
print( debug.getmetatable( values[i] ) )
|
print( type(values[i]), 'before', ecall( 'attempt to get length of ', function() return #values[i] end ) )
|
||||||
|
print( debug.setmetatable( values[i], mt ) )
|
||||||
|
print( type(values[i]), 'after', pcall( function() return #values[i] end ) )
|
||||||
|
print( debug.setmetatable( values[i], nil ) )
|
||||||
end
|
end
|
||||||
|
|
||||||
|
print( '---- __neg' )
|
||||||
|
values = { aboolean, afunction, athread, "abcd" }
|
||||||
|
for i=1,#values do
|
||||||
|
print( type(values[i]), 'before', ecall( 'attempt to get length of ', function() return #values[i] end ) )
|
||||||
|
print( debug.setmetatable( values[i], mt ) )
|
||||||
|
print( type(values[i]), 'after', pcall( function() return #values[i] end ) )
|
||||||
|
print( debug.setmetatable( values[i], nil ) )
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
Reference in New Issue
Block a user