void main() { debug_message("%O","hello" == "hello"); debug_message("%O",[1,2]==[1,2]); }
这段lpc代码会输出什么呢?
我们先从字节码分析吧。
引用
STRINGS:
0: a.c
1: %O
2: hello
0000: push string 1, string 2, string 2
0005: ==
0006: debug_message 2
0009: push string 1, number 1, number 2
000e: aggregate 2
0011: push number 1, number 2
0015: aggregate 2
0018: ==
0019: debug_message 2
001c: return_zero
红色的这四行先在栈顶上创建了两个数组。先push数字,再aggregate出数组
aggregate 对应的代码:
{ array_t *v; LOAD_SHORT(offset, pc); offset += num_varargs; num_varargs = 0; v = allocate_empty_array( (int)offset); /* * transfer svalues in reverse...popping stack as we go */ while (offset--) { v->item[offset] = *sp--; } (++sp)->type = T_ARRAY; sp->u.arr = v; }
num_varargs由F_EXPAND_VARARGS字节码来赋值,用于以下情况
int *i = [1,2];
int *j = [3,i...];
num_varargs就是1
至此两个数组已经创建出来了。
这与Java中的数组创建方式不一样。Java是先分配数组,再根据下标来给分配好的数组赋值。字节码多点,但粒度更细更灵活。
引用
0: iconst_2
1: newarray int
3: dup
4: iconst_0
5: bipush 10
7: iastore
8: dup
9: iconst_1
10: bipush 20
12: iastore
接下来就是==字节码了。
void f_eq(){ …… case T_STRING: { if (SVALUE_STRLEN_DIFFERS(sp - 1, sp) ) { i = 0; } else { i = !strcmp( (sp - 1)->u.string, sp->u.string); } free_string_svalue(sp--); free_string_svalue(sp); break; } case T_ARRAY: { i = (sp - 1)->u.arr == sp->u.arr; free_array( (sp--)->u.arr); free_array(sp->u.arr); break; } …… }
两个数组==比较,只是比较了地址。所以输出是1 0
但数组在lpc中比较地址,有什么意义呢?python是比较数组内容的,我觉得可以改善一下。
作者:翁志艺