博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
do{}while(0)与CC_BREAK_IF的绝妙搭配
阅读量:4626 次
发布时间:2019-06-09

本文共 2520 字,大约阅读时间需要 8 分钟。

从一開始认为没有必要,到认为很好用。我经历了大概两个月的时间,以下来总结一下什么情况下使用这样的结构吧。

第一种情况:当载入文件的时候,假设载入文件失败,须要报错的时候。

当前,能够用try{}catch(){}finally{}这样的结构。可是这样做会极大的添加编译后文件的大小。使用do{}while(0)加上CC_BREAK_IF就能实现一样的效果,并且不添加文件的大小。

以下是一个样例:

bool GameScene::setScene(){	do{		auto node = SceneReader::getInstance()->createNodeWithSceneFile("publish/GameScene.csb");  		CC_BREAK_IF(!node);		m_UI_Background->addChild(node);		auto Checkerboard = (ComRender*)(node->getChildByTag(10009)->getComponent("GUIComponent"));		CheckerboardUI = Checkerboard->getNode();		//设置button		m_btn_Setting = dynamic_cast
(CheckerboardUI->getChildByName("Button_Setting")); CC_BREAK_IF(!m_btn_Setting); //音乐button m_btn_Music = dynamic_cast
(CheckerboardUI->getChildByName("Button_Music")); CC_BREAK_IF(!m_btn_Music); //棋盘锁 m_btn_Lock = dynamic_cast
(CheckerboardUI->getChildByName("Button_Lock")); CC_BREAK_IF(!m_btn_Lock); //棋盘图片 m_Image_Checkerboard = dynamic_cast
(CheckerboardUI->getChildByName("Image_Checkerboard")); CC_BREAK_IF(!m_Image_Checkerboard); m_Checkerboard = Checkerboard::create(m_Image_Checkerboard); auto SelectPeople = (ComRender*)(node->getChildByTag(10031)->getComponent("GUIComponent")); SelectPeopleUI = SelectPeople->getNode(); this->setCampBtn(); return true; }while(0); CCLOG("ERROR:Load Resources Fail in GameScene::setScene"); return false;}
假设在中途出现不论什么一个变量运行后还是nullptr。那么就CC_BREAK_IF,然后显示错误日志。最后返回false给上层函数进行处理。这种处理方式是不是既优雅又方便高速,又避免了可能错误使用空指针。

另外一种情况:当不管怎样都须要在函数最后进行清理操作的时候。

以下举一个比較典型的样例,就是在函数开头声明了一个new的指针(非智能指针),依照正常的流程,须要delete。可是我们无法保证程序会不会在中途就return了,由于兴许的维护者并不知道还有这个清除操作须要运行。以下是一个对照样例:

//errorvoid test(){	GameScene* gamescene = new GameScene;	// doSomething...	if(gamescene->getChildByTag(111) == nullptr)	{		return;	}	// doSomething...	delete gamescene;	gamescene = nullptr;}//rightvoid test1(){	GameScene* gamescene = new GameScene;	do{		// doSomething...		CC_BREAK_IF(gamescene->getChildByTag(111) == nullptr);		// doSomething...	}while(0);	delete gamescene;	gamescene = nullptr;}
使用CC_BREAK_IF能够保证永远都会运行到最后两行,也就不会出现内存泄露。

可是这个组合也不是万能的,以下就说一个不适合这样的结构的情况吧。

当do{}while(0)的括号里存在循环的时候,就不适用这个组合了。由于break毕竟仅仅能跳出一层循环,以下是一个样例:

void test2(){	do{		for(int i = 0;i <5;++i)		{			// doSomething...			CC_BREAK_IF(i>4); 			// doSomething...		}		CCLOG("永远显示这一行日志");	}while(0);}
我们希望的是,CC_BREAK_IF能跳出do{}while(0)循环。可是实际上。仅仅跳出了for循环,所以使用do{}while(0)和CC_BREAK_IF的时候,须要确保其内部不能存在其它循环,假设存在循环,还是建议使用try{}catch(){}

转载于:https://www.cnblogs.com/liguangsunls/p/6767916.html

你可能感兴趣的文章
ALL about SYSDBA and SYSOPER Privileges in Oracle [ID 50507.1]
查看>>
JSON.parseObject笔记
查看>>
倒车入库太难了?掌握技巧,其实它也可以很简单
查看>>
怎么开手动档轿车?这么开让你再也不想开自动档
查看>>
FileSystemXmlApplicationContext、ClassPathXmlApplicationContext和XmlWebApplicationContext简介
查看>>
java native方法及JNI实例
查看>>
9_2019.04.20随记
查看>>
29 最小的K个数
查看>>
10款免费且开源的项目管理工具
查看>>
thinkphp数据查询方法总结select ,find,getField,query
查看>>
Spring Boot控制上传文件大小
查看>>
Wannafly挑战赛22 A计数器(裴蜀定理 gcd)
查看>>
day22作业详解
查看>>
Codeforces 10D
查看>>
charles抓包
查看>>
新手上路注意事项及驾车技巧
查看>>
关于Block汇总
查看>>
freemarker 学习一 入门小例子
查看>>
获取bing每日图片
查看>>
图解Docker容器和镜像
查看>>