c++ primer读书笔记——第5章 语句(2019.9.5)

第5章 语句

5.1 简单语句

表达式末尾加上分号就变为表达式语句,表达式语句的作用是执行表达式并丢弃掉求值结果

ival+5;

空语句:当循环的全部工作在条件部分就可以完成时,通常会使用空语句

while(cin>>s && s!=sought);

块:用花括号括起来的语句序列

5.2 语句作用域

一个块就是一个作用域

5.3 条件语句

5.3.1 if语句

悬垂else:怎么知道某个给定的else是和哪个if匹配呢?与离他最近且尚未匹配的if匹配

5.3.2 switch语句

switch首先对括号内的表达式求值,然后将表达式的值转换成整数类型,与case的每一个标签比较。如果和某个标签匹配成功,从该标签之后的第一条语句开始执行,直到到达了switch的结尾或者遇到一条break语句为止。
case和它对应的值一起被称为case标签,case标签必须是整型常量表达式,任何两个case标签的值不能相同。
default也是一种特殊的case标签
在大多数情况下,下一个case标签之前应该有一条break语句。如果没写break语句,最好加一段注释说明程序逻辑
尽管switch语句不是非得在最后一个标签后面写上break,但是为了安全起见,最好这么做。如果以后增加新的分支就不用在前面补充break语句。
如果没有任何一个case标签能匹配上switch表达式的值,程序将执行紧跟在default标签后面的语句。即使不准备在default标签下做任何工作,定义一个default标签也是有用的,说明我们已经考虑到了默认的情况。
标签不应该孤零零地出现,后面必须跟上一条语句或者另外一个case标签,特别注意最后一个标签。
如果要为某个case分支定义并初始化一个变量,我们应该把变量定义在块内,从而确保后面的所有case标签都在变量的作用域之外。

5.4 迭代语句

while和for在执行循环体前检查条件,do while是先执行循环体再检查条件

5.4.1 while语句

如果检查条件第一次就为false,则循环体一次都不执行
定义在while条件部分或者while循环体内的变量每次迭代都经历从创建到销毁的过程
当不确定要迭代多少次时,使用while循环比较合适。
如果想在循环结束后访问循环控制变量,也需要使用while循环

5.4.2 传统for语句

如果检查条件第一次就为false,则循环体一次都不执行
for语句头定义的对象只在for循环体中可见

5.4.3 范围for语句

范围for语句是c++ 11新特性,用于遍历容器或者其他序列的所有元素,其语法形式:

for(declaration: expression)
  statement

expression必须是一个序列,拥有能返回迭代器的begin和end
declaration定义一个变量,序列中的每个元素都能转换成该变量的类型。确保类型相容的最简单的办法是使用auto。如果需要对序列中的元素执行写操作,需要把declaration定义成引用类型。
每次迭代都会重新定义循环控制变量,将其初始化为序列中的下一个值,之后执行statement。所有元素执行完毕后循环终止。
与范围for语句等价的传统for语句

for(auto beg=v.begin(),end=v.end();beg!=end;++beg)
{
   ...
}

因为范围for语句预存了end()的值,所以不能在使用范围for语句时执行改变序列长度的操作

5.4.4 do while语句

不管条件值如何,都至少会执行一次循环。
do while语句应该在括号包围起来的条件后用一个分号表示语句结束
do while语句先执行循环体再判断条件,所以不允许在条件部分定义变量

5.5 跳转语句

c++语言提供了4种跳转语句:break continue goto return

5.5.1 break语句

终止离它最近的while,do while,for或者switch语句,并从这些语句后的第一条语句开始继续执行
break只能出现在循环语句或者switch语句内部
break的作用范围仅限于最近的循环或者switch

5.5.2 continue语句

终止最近的循环的当前迭代并且立即开始下一次迭代
continue只出现在循环语句内部
continue仅作用于离它最近的循环

5.5.3 goto语句

不要在程序中使用goto语句
作用是从goto语句无条件跳转到同一函数内的另一条语句
语法形式:goto label;
label是用于标识一条语句的标示符。带标签语句是一种特殊的语句,在它之前有一个标示符及一个冒号
goto语句和控制权转向的那条带标签的语句必须位于同一个函数内

5.6 TRY语句块和异常处理

异常处理机制为异常检测异常处理提供支持,包括:
①throw表达式:异常检测

throw runtime_error("XXX");  //部分异常类型必须要初始化,部分不能进行初始化(如bad_alloc)

②try语句块:异常处理,以关键字try开始,以一个或多个catch子句结束,try语句块中异常会被某个catch子句处理(多选一)

5.6.1 throw表达式

异常检测部分使用throw表达式引发一个异常。
形式:throw 表达式;例如:

if(XXX)
throw runtime_error("xxxx");

标准库异常类型定义在头文件stdexcept中
必须初始化runtime_error对象,方式是给它提供一个string对象或c风格字符串

5.6.2 try语句块

形式:

 try
 {
   //可能抛出异常的语句块
   if(XXX)
   throw runtime_error("xxxx");
 }
 catch(runtime_error er)
 {
    //做出相应处理
 }
 catch(XXX)
 {
   //做出相应处理
 }

try后面紧跟着一个块,跟在try块后面的是一个或多个catch子句,catch子句包括catch、括号内一个对象的声明、一个块。当选中某个catch子句执行对应的块,执行完成,跳转到try语句块最后一个catch子句之后的那条语句继续执行

5.6.3 标准异常

c++标准库定义了一组类,用于报告标准库函数遇到的问题
标准库异常类有成员函数what(),返回值为初始化string的副本

 try
 {
   //可能抛出异常的语句块
   if(XXX)
   throw runtime_error("data must refer to same ISBN");
 }
 catch(runtime_error er)
 {
    cout<

er.what()的结果是data must refer to same ISBN,what()的返回值是指向c风格字符串的const char *,该字符串是含有错误相关的信息

寻找处理代码的过程与函数调用链刚好相反,由内到外,逐层回退,直到找到匹配的catch子句为止。如果没有找到任何匹配的catch子句或者没有定义try异常处理,程序会执行terminate的标准库函数,执行该函数会导致程序非正常退出

标准库异常类的初始化方式:
①exception,bad_alloc,bad_cast只能以默认初始化的方式初始化,不允许为对象提供初始值
②其余异常类需要显式初始化,必须提供初始值(string或者c风格字符串),该初始值含有错误相关的信息。

你可能感兴趣的:(c++,primer读书笔记)