lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


Hello,
thanks for all help at now !

I try :

<...>
    lua_newtable(L); // create 'mastertable'

    lua_newtable(L); // create 'table1'
    luaL_getmetatable(L, "luasystem.mastertable"); // get metatable
from the registry
    lua_setmetatable(L, -2); // setmetatable(table1, __mt)
    luaL_register(L, NULL, meths);
    lua_setfield(L, -2, "table1");

    lua_newtable(L);
    lua_setfield(L, -2, "table2");

    lua_newtable(L);
    lua_setfield(L, -2, "table3");

    lua_setglobal(L,"mastertable");
<...>

>> type(persistent)=table
>> type(persistent.service)=table
>> type(persistent.channel)=table
>> type(persistent.shared)=table
>> persistent.service.a=7

But again l_index and l_newindex was never called...
Really I need to understand the lua stack concepts and how to "link"
these lua objects.


Thanks
Flávio Lopes

2014-09-05 22:38 GMT-03:00 Peng Zhicheng <pengzhicheng1986@gmail.com>:
> On 09/05/2014 10:53 PM, Flávio Alberto wrote:
>>
>> Excuse-me, my last e-mail was sent in HTML mode, set in simple text
>> mode...
>>
>> Hello all
>> I'm a C/C++ programmer and new to Lua, I'm need a requirement on my
>> application, I need that a lua script access a previous created global
>> table and inside this table I need to have more three tables,  these
>> table creation was made in C system using this code :
>>
>>
>> static int l_index(lua_State* L)
>> {
>>    cout << __FILE__ << " : " << __FUNCTION__ << endl;
>>    return 1;
>> }
>>
>> static int l_newindex(lua_State* L)
>> {
>>      cout << __FILE__ << " : " << __FUNCTION__ << endl;
>>    return 1;
>> }
>>
>> static const struct luaL_Reg methods[] = {
>> { "__index",       l_index },
>> { "__newindex",    l_newindex },
>> { NULL,            NULL            }
>> };
>>
>>
>> LUALIB_API int luaopen_mastertable (lua_State* L)
>> {
>>      luaL_newmetatable(L, "luasystem.mastertable");
>>    lua_pushvalue(L, -1);
>>
>>    luaL_register(L, NULL, methods);
>>    lua_pop(L, 1);
>>    lua_pushnil(L);
>>
>>      lua_pushnumber(L,0);
>>      lua_newtable(L);
>>      lua_pushliteral(L,"table1");
>>      lua_newtable(L);
>>
>>      lua_pushliteral(L,"table2");
>>      lua_newtable(L);
>>
>>      lua_pushliteral(L,"table3");
>>      lua_newtable(L);
>>
>>      lua_settable(L,-7);
>>      lua_settable(L,-5);
>>      lua_settable(L,-3);
>>
>>      lua_setglobal(L,"mastertable");
>>
>>    return 1;
>> }
>>
>> and in main code I do :
>>
>> .
>> .
>> .
>> luaopen_mastertable(this->L, NULL, 0);
>> luaL_loadfile(...);
>> lua_pcall(...);
>> .
>> .
>> .
>>
>> When running the folowing script :
>>
>> print(">> type(mastertable)="..type(mastertable))
>> print(">> type(mastertable.table1)="..type(mastertable.table1))
>> print(">> type(mastertable.table2)="..type(mastertable.table2))
>> print(">> type(mastertable.table3)="..type(mastertable.table3))
>>
>> mastertable.table1.a = 7
>> mastertable.table1.b = {}
>>
>> print(">> mastertable.table1.a="..mastertable.table1.a)
>>
>>
>> I get the following messages on terminal :
>>>>
>>>> type(mastertable)=table
>>>> type(mastertable.table1)=table
>>>> type(mastertable.table2)=table
>>>> type(mastertable.table3)=table
>>>> mastertable.table1.a=7
>>
>> I look that my C code created the tables OK, but l_index()
>> l_newindex() were not called.
>> Whats the problem with the registration of these calls ? What is the
>> correct way to do this ?
>>
>> Thanks for any help
>> Success
>>
>> Flávio Lopes
>>
> luaL_newmetatable would only create (or reuse pre-existing) a table to be
> used as a
> metatable and store it into the registry using the given tname as key.
> you still need to call lua_setmetatable.
>
> besides, metatables for tables and full userdata are in per-instance basis,
> you need
> to call lua_setmetatable on each table instance you want to associate the
> metatable.
>
> yet metatables for other builtin data types (boolean, number, etc) are
> per-type, which
> means all the values of the same type share the same metatable, so you need
> only
> call lua_setmetatable once on any value of that type.
>
> in your example, if you want register the metatable for
> `mastertable.table1`:
>
> ~~~~
>
> <...>
>
> lua_newtable(L); // create 'mastertable'
>
> lua_newtable(L); // create 'table1'
> luaL_getmetatable(L, "tname of your metatable"); // get metatable from the
> registry
> lua_setmetatable(L, -2); // setmetatable(table1, __mt)
> lua_setfield(L, -2, "table1");
>
> lua_newtable(L);
> lua_setfield(L, -2, "table2");
>
> lua_newtable(L);
> lua_setfield(L, -2, "table3);
>
> lua_setglobal(L,"mastertable");
>
> <...>
>
> ~~~~
>
> thus, ``mastertable.table1.a = 7`` would trigger the __newindex metamethod,
> and
> ``print(mastertable.table1.a)`` would trigger the __index metamethod, and
> would
> print out 'nil', as the __index metamethod returned nothing, but Lua would
> adjust
> it into 1 value, resulting the 'nil'
>
>
>