【C语言笔记】【有点逗系列】 使用goto语句实现switch语句的功能
有点逗系列内容。用于记录各式各样有点逗甚至没有什么用的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("lable0\n");
goto end;
lable1:
printf("lable1\n");
goto end;
lable2:
printf("lable2\n");
goto end;
lable3:
printf("lable3\n");
goto end;
lable4:
printf("lable4\n");
goto end;
lable5:
printf("lable5\n");
goto end;
other:
printf("other %d\n", 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("lable0\n");
break;
case 1:
printf("lable1\n");
break;
case 2:
printf("lable2\n");
break;
case 3:
printf("lable3\n");
break;
case 4:
printf("lable4\n");
break;
case 5:
printf("lable5\n");
break;
default:
printf("other %d\n", 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("lable0\n");
goto end;
这个类似于case
:
case 0:
printf("lable0\n");
break;
其中的goto end
相当于break
。
还需要应对其他情况:
if(val >= (sizeof(array)/sizeof(void*)))
goto other;
other:
printf("other %d\n", val);
这个类似于default
:
default:
printf("other %d\n", val);
这样就实现了使用goto语句实现switch语句的功能。
[参考资料]
本文链接:https://blog.csdn.net/u012028275/article/details/122444065