有点逗系列内容。用于记录各式各样有点逗甚至没有什么用的C语言用法☺。
功能说明功能就是使用goto语句实现switch语句的功能。
该功能基于GNU对C语言扩展功能:标签作为值(Labels as Values)。
也就是对Labels as Values这个扩展功能的一种使用方式,实现的这个switch功能实际并没啥用。
实现代码void goto_switch(unsigned int val) { static void* array[] = { &&lable0, &&lable1, &&lable2, &&lable3, &&lable4, &&lable5}; if(val >= (sizeof(array)/sizeof(void*))) goto other; goto *array[val]; lable0: printf("lable0n"); goto end; lable1: printf("lable1n"); goto end; lable2: printf("lable2n"); goto end; lable3: printf("lable3n"); goto end; lable4: printf("lable4n"); goto end; lable5: printf("lable5n"); goto end; other: printf("other %dn", val); end: return; }
这个程序就是使用goto语句实现switch语句的功能,实现的效果就是val的值为0,1,2,3,4,5的时候打印lable0,lable1,lable2,lable3,lable4,lable5,其他值的话直接打印出来。
效果与下面的这个使用switch语句的程序相同。
void real_switch(unsigned int val) { switch(val) { case 0: printf("lable0n"); break; case 1: printf("lable1n"); break; case 2: printf("lable2n"); break; case 3: printf("lable3n"); break; case 4: printf("lable4n"); break; case 5: printf("lable5n"); break; default: printf("other %dn", val); } return; }示例程序
int main(int argc, char* argv[]) { for(int i = 0; i < 10; i++) goto_switch(i); return 0; }
运行结果就是:
lable0 lable1 lable2 lable3 lable4 lable5 other 6 other 7 other 8 other 9实现原理
实现的原理就是基于GNU对C语言扩展功能Labels as Values。
GNU的Labels as Values功能就是,可以使用运算符“&&”获取当前函数中定义的标签(label)的地址,值的类型为void *。如下:
void *ptr; ptr = &&foo;
要使用这个值的方式如下:
goto *ptr;
该功能允许使用void*类型的任何表达式。
基于上述的功能,接下来就可以使用goto语句实现switch语句的功能了。
先要定义要有多少分支,如下:
static void* array[] = { &&lable0, &&lable1, &&lable2, &&lable3, &&lable4, &&lable5};
跳转方式如下:
goto *array[val];
这个类似于switch:
switch(val)
将预先定义好的分支对应的标签实现好:
lable0: printf("lable0n"); goto end;
这个类似于case:
case 0: printf("lable0n"); break;
其中的goto end相当于break。
还需要应对其他情况:
if(val >= (sizeof(array)/sizeof(void*))) goto other;
other: printf("other %dn", val);
这个类似于default:
default: printf("other %dn", val);
这样就实现了使用goto语句实现switch语句的功能。
[参考资料]【GNU笔记】【C扩展系列】标签作为值
6.3 Labels as Values
本文链接:https://blog.csdn.net/u012028275/article/details/122444065
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)