diff options
Diffstat (limited to 'lbaselib.c')
-rw-r--r-- | lbaselib.c | 46 |
1 files changed, 41 insertions, 5 deletions
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | ** $Id: lbaselib.c,v 1.291 2014/07/16 13:56:59 roberto Exp roberto $ | 2 | ** $Id: lbaselib.c,v 1.292 2014/07/17 13:53:37 roberto Exp roberto $ |
3 | ** Basic library | 3 | ** Basic library |
4 | ** See Copyright Notice in lua.h | 4 | ** See Copyright Notice in lua.h |
5 | */ | 5 | */ |
@@ -244,17 +244,53 @@ static int luaB_pairs (lua_State *L) { | |||
244 | } | 244 | } |
245 | 245 | ||
246 | 246 | ||
247 | static int ipairsaux (lua_State *L) { | 247 | /* |
248 | int i = luaL_checkint(L, 2); | 248 | ** Traversal function for 'ipairs' for raw tables |
249 | */ | ||
250 | static int ipairsaux_raw (lua_State *L) { | ||
251 | int i = luaL_checkint(L, 2) + 1; | ||
249 | luaL_checktype(L, 1, LUA_TTABLE); | 252 | luaL_checktype(L, 1, LUA_TTABLE); |
250 | i++; /* next value */ | ||
251 | lua_pushinteger(L, i); | 253 | lua_pushinteger(L, i); |
252 | return (lua_rawgeti(L, 1, i) == LUA_TNIL) ? 1 : 2; | 254 | return (lua_rawgeti(L, 1, i) == LUA_TNIL) ? 1 : 2; |
253 | } | 255 | } |
254 | 256 | ||
255 | 257 | ||
258 | /* | ||
259 | ** Traversal function for 'ipairs' for tables with metamethods | ||
260 | */ | ||
261 | static int ipairsaux (lua_State *L) { | ||
262 | int i = luaL_checkint(L, 2) + 1; | ||
263 | if (i > luaL_len(L, 1)) { /* larger than length? */ | ||
264 | lua_pushnil(L); /* end traversal */ | ||
265 | return 1; | ||
266 | } | ||
267 | else { | ||
268 | lua_pushinteger(L, i); | ||
269 | lua_pushinteger(L, i); /* key for indexing table */ | ||
270 | lua_gettable(L, 1); | ||
271 | return 2; | ||
272 | } | ||
273 | } | ||
274 | |||
275 | |||
276 | /* | ||
277 | ** This function will use either 'ipairsaux' or 'ipairsaux_raw' to | ||
278 | ** traverse a table, depending on whether the table has metamethods | ||
279 | ** that can affect the traversal. | ||
280 | */ | ||
256 | static int luaB_ipairs (lua_State *L) { | 281 | static int luaB_ipairs (lua_State *L) { |
257 | return pairsmeta(L, "__ipairs", 1, ipairsaux); | 282 | lua_CFunction iter = |
283 | (luaL_getmetafield(L, 1, "__len") || | ||
284 | luaL_getmetafield(L, 1, "__index")) | ||
285 | ? ipairsaux : ipairsaux_raw; | ||
286 | #if defined(LUA_COMPAT_IPAIRS) | ||
287 | return pairsmeta(L, "__ipairs", 1, iter); | ||
288 | #else | ||
289 | lua_pushcfunction(L, iter); /* iteration function */ | ||
290 | lua_pushvalue(L, 1); /* state */ | ||
291 | lua_pushinteger(L, 0); /* initial value */ | ||
292 | return 3; | ||
293 | #endif | ||
258 | } | 294 | } |
259 | 295 | ||
260 | 296 | ||