klv*_*oek 4 javascript c pointers logical-operators
在C中,当有变量(假设两者都小于int)时,我们可以使用等式 ij
i^=j^=i^=j
Run Code Online (Sandbox Code Playgroud)
交换两个变量的值.例如,让int i = 3,j = 5; 经过计算i^=j^=i^=j,我有i = 5,j = 3.
但是,如果我使用两个int指针重新执行此操作*i^=*j^=*i^=*j,使用上面的示例,我将拥有i = 0和j = 3.
int i=3, j=5;
i^=j^=i^=j; // after this i = 5, j=3
Run Code Online (Sandbox Code Playgroud)
int i = 3, j= 5;
int *pi = &i, *pj = &j;
*pi^=*pj^=*pi^=*pj; // after this, $pi = 0, *pj = 5
Run Code Online (Sandbox Code Playgroud)
在JavaScript中
var i=3, j=5;
i^=j^=i^=j; // after this, i = 0, j= 3
Run Code Online (Sandbox Code Playgroud)
JavaScript中的结果使我对此更感兴趣
我的示例代码,在ubuntu服务器11.0和gcc上
#include <stdio.h>
int main(){
int i=7, j=9;
int *pi=&i, *pj=&j;
i^=j^=i^=j;
printf("i=%d j=%d\n", i, j);
i=7, j=9;
*pi^=*pj^=*pi^=*pj
printf("i=%d j=%d\n", *pi, *pj);
}
Run Code Online (Sandbox Code Playgroud)
c中未定义的行为是导致这个问题的真正原因吗?
代码编译使用Visual Studio 2005在Windows 7上产生预期的结果(输出i = 7,j = 9两次.)
代码编译在ubuntu(gcc test.c)上使用gcc产生意外结果(输出i = 7,j = 9然后i = 0,j = 9)
代码编译使用uccntu上的gcc(gcc -O test.c)产生预期的结果(输出i = 7,j = 9两次.)
i^=j^=i^=j 在C中是未定义的行为
您通过i在两个序列点之间修改两次来违反序列点规则.
这意味着实现可以自由分配任何值,甚至使程序崩溃.
出于同样的原因,*i^=*j^=*i^=*j也是未定义的行为.
(C99,6.5p2)"在前一个和下一个序列点之间,一个对象的存储值最多只能通过表达式的评估来修改一次."