之前在博文中说过do while(0)的用法, 不过实际项目中用得不多。 最近遇到麻烦了, 感觉到不用do while(0)就很蛋疼。

         先来看一段比较常规的丑代码:

 

#include<iostream>
using namespace std;

int fun(int a, int b, int c, int d)
{
	int errCode = 0;
	if(a < 0)
	{
		errCode = -1;
		printf("error1\n");

		printf("code xxx, err code is %d\n", errCode);
		printf("code yyy, err code is %d\n", errCode);
		printf("code zzz, err code is %d\n", errCode);
		return errCode;
	}

	int r1 = 0;

	if(b < 0)
	{
		errCode = -2;
		printf("error2\n");

		printf("code xxx, err code is %d\n", errCode);
		printf("code yyy, err code is %d\n", errCode);
		printf("code zzz, err code is %d\n", errCode);
		return errCode;
	}

	int r2 = 0;

	if(c < 0)
	{
		errCode = -3;
		printf("error3\n");

		printf("code xxx, err code is %d\n", errCode);
		printf("code yyy, err code is %d\n", errCode);
		printf("code zzz, err code is %d\n", errCode);
		return errCode;
	}

	int r3 = 0;

	if(d < 0)
	{
		errCode = -4;
		printf("error4\n");

		printf("code xxx, err code is %d\n", errCode);
		printf("code yyy, err code is %d\n", errCode);
		printf("code zzz, err code is %d\n", errCode);
		return errCode;
	}

	int r4 = 0;


	// add normal business logic here


	printf("code xxx, err code is %d\n", errCode);
	printf("code yyy, err code is %d\n", errCode);
	printf("code zzz, err code is %d\n", errCode);
	return errCode;
}


int main()
{
	fun(-1, -1, -1, -1);
	return 0;
}

       我们可以看到, 代码存在极大的冗余, 一坨一坨的, 像什么样!  于是, 有的人说用goto可以搞定啊。 且不说goto为人诟病已久, 先来看看goto的效果:

 

 

#include<iostream>
using namespace std;

int fun(int a, int b, int c, int d)
{
	int errCode = 0;
	if(a < 0)
	{
		errCode = -1;
		printf("error1\n");

		goto END;
	}

	int r1 = 0;

	if(b < 0)
	{
		errCode = -2;
		printf("error2\n");

		goto END;
	}

	int r2 = 0;

	if(c < 0)
	{
		errCode = -3;
		printf("error3\n");

		goto END;
	}

	int r3 = 0;

	if(d < 0)
	{
		errCode = -4;
		printf("error4\n");

		goto END;
	}

	int r4 = 0;


	// add normal business logic here


END:
	printf("code xxx, err code is %d\n", errCode);
	printf("code yyy, err code is %d\n", errCode);
	printf("code zzz, err code is %d\n", errCode);
	return errCode;
}


int main()
{
	fun(-1, -1, -1, -1);
	return 0;
}

       经验比较丰富的同学一眼就可以看出问题, 这里存在编译问题。 在linux GCC下提示:crosses initialization of xxx,  在Windows VC++下提示:initialization of 'r4' is skipped by 'goto END'

 

       那怎么办呢? 也不是完全么有办法, 方法1是把所有被跳过的变量放在最前面定义, 方法2是直接用大括号把被掉过的变量括起来。 在实际中, 这两种方法我都玩过。 第一种方法非常繁琐(当时搞一个安全问题, 写代码的时候用了这个方式), 要重新移动变量的位置, 而第二种方法显得很猥琐(当时是搞一个节日活动的问题, 写代码的时候用了这种方式), 谁用谁知道。

       还是来看看do while(0)的实现方式吧, 我最近就是这么搞的, 相对较爽:

 

#include<iostream>
using namespace std;

int fun(int a, int b, int c, int d)
{
	int errCode = 0;

	do 
	{
		if(a < 0)
		{
			errCode = -1;
			printf("error1\n");

			break;
		}

		int r1 = 0;

		if(b < 0)
		{
			errCode = -2;
			printf("error2\n");

			break;
		}

		int r2 = 0;

		if(c < 0)
		{
			errCode = -3;
			printf("error3\n");

			break;
		}

		int r3 = 0;

		if(d < 0)
		{
			errCode = -4;
			printf("error4\n");

			break;
		}

		int r4 = 0;
	}while(0);

	// add normal business logic here

	printf("code xxx, err code is %d\n", errCode);
	printf("code yyy, err code is %d\n", errCode);
	printf("code zzz, err code is %d\n", errCode);
	return errCode;
}


int main()
{
	fun(-1, -1, -1, -1);
	return 0;
}

        搞定!

 

 

 


本文转载:CSDN博客