《C++ Primer Plus》第六章总结

一、if语句

if语句的语法与while 相似:

if (test-condition)
        statement

如果test-condition(测试条件)为true,则程序将执行statement(语句),后者既可以是一条语句,也可以是语句块。如果测试条件为false,则程序将跳过语句。和循环测试条件一样,if测试条件也将被强制转换为bool值,因此0将被转换为false,非零为true。整个if语句被视为一条语句。通常情况下,测试条件都是关系表达式,如那些用来控制循环的表达式。

#include <iostream>
using namespace std;

int main()
{
	char ch;
	int spaces = 0;
	int total = 0;
	cin.get (ch) ;
	while (ch != '.')
	{
		if (ch == ' ') // check if ch is a space
		++spaces;
		++total;
		cin.get (ch) ;
	}
	cout << spaces << " spaces, " << total;
	cout << " characters total in sentence\n";
	return 0;
 } 

1.if else语句

if语句让程序决定是否执行特定的语句或语句块,而if else语句则让程序决定执行两条语句或语句块中的哪一条,下面是它的通用格式:

if (test-condition)
        statement1;
else
        statement2;

如果测试条件为true或非零,则程序将执行statement1,跳过 statement2;如果测试条件为false或0,则程序将跳过 statement1,执行statement2。从语法上看,整个if else结构被视为一条语句。

#include <iostream>
using namespace std;

int main()
{
	char ch;
	cout << "Type, and I shall repeat.\n";
	cin.get (ch) ;
	while (ch != '.')
	{
		if (ch == '\n') 
		cout<<ch;
		else
		cout<<++ch;
		cin.get (ch) ;
	}
	cout << "\nPlease excuse the slight confusion.\n";
	return 0;
 } 

如果将++ch换为ch+1,那么它输出的是数字,因为1的存在,将ch+1类型提升为int类型,输出的也是int类型。如果想要输出字符,那么可以使用强制类型转换。

2.if else if else结构

与实际生活中发生的情况类似,计算机程序也可能提供两个以上的选择。可以将C++的if else语句进行扩展来满足这种需求。else之后应是一条语句,也可以是语句块。由于if clse语句本身是一条语句,所以可以放在else的后面:

if (ch == 'A')
        a_grade++;
else
        if (ch == 'B')
                b_grade++;
        else

                soso++;

C++的自由格式允许将这些元素排列成便于阅读的格式:

if (ch == 'A')
        a_grade++;
else if (ch == 'B')
        b_grade++;
else
        soso++;

这看上去像是一个新的控制结构if else if else 结构。但实际上,它只是一个 if else被包含在另一个if else 中。修订后的格式更为清晰,使程序员通过浏览代码便能确定不同的选择。整个构造仍被视为一条语句。

#include <iostream>
using namespace std;
const int Fave = 27;
int main()
{
	int n;
	cout << "Enter a number in the range 1-100 to find my favorite number: ";
	do
	{
		cin >> n;
		if (n < Fave)
			cout << "Too low -- guess again: ";
		else if (n > Fave)
			cout << "Too high -- guess again: ";
		else
			cout << Fave << " is right!\n";
	} while (n != Fave) ;
	return 0;
 } 

小技巧:可以将variable==value写为value==variable,来防止将==写为=。

二、逻辑表达式

1.逻辑OR运算符:||

||的优先级比关系运算符低,C++规定,||运算符是个顺序点。也是说,先修改左侧的值,再对右侧的值进行判定,C++11的说法是,运算符左边的子表达式先于右边的子表达式。另外,如果左侧的表达式为true,则C++将不会去判定右侧的表达式,因为只要一个表达式为true,则整个逻辑表达式为true。

#include <iostream>
using namespace std;

int main()
{
	cout << "This program may reformat your hard disk\n"
		"and destroy all your data.\n"
		"Do you wish to continue? <y/n> ";
	char ch;
	cin >> ch;
	if (ch == 'y' || ch == 'Y')
		cout << "You were warned! \a\a\n";
	else if (ch == 'n' || ch == 'N')
		cout << "A wise choice ... bye\n";
	else
		cout << "That wasn't a y or n! Apparently you "
			"can't follow\ninstructions, so "
			"I'll trash your disk anyway. \a\a\a\n";
	return 0;
 } 

2.逻辑AND运算符:&&

&&的优先级低于关系运算符,且和||运算符一样,&&运算符也是顺序点,因此将首先判定左侧,并且在右侧被判定之前产生所有的副作用。如果左侧为false,则整个逻辑表达式必定为false,在这种情况下,C++将不会再对右侧进行判定。

#include <iostream>
using namespace std;
const int ArSize = 6;
int main()
{
	float naaq[ArSize];
	cout << "Enter the NAAQs (New Age Awareness Quotients) "
		<< "of\nyour neighbors. Program terminates "
		<< "when you make\n" << ArSize << " entries "
		<< "or enter a negative value.\n";
	int i = 0;
	float temp;
	cout << "First value: ";
	cin >> temp;
	while (i < ArSize && temp >= 0)
	{
		naaq[i] = temp;
		++i;
		if (i < ArSize)
		{
			cout << "Next value: ";
			cin >> temp;
		}
	}
	if (i == 0)
		cout << "No data -- bye\n";
	else
	{
		cout << "Enter your NAAQ: ";
		float you;
		cin >> you;
		int count = 0;
		for (int j = 0; j < i; j++)
			if (naaq[j] > you)
			++count ;
		cout << count;
		cout << " of your neighbors have greater awareness of\n"
			<< "the New Age than you do.\n";
	}
	return 0;
 } 

3.用&&来设置取值范围

#include <iostream>
using namespace std;
const char * qualify [4] =
{
	"10,000-meter race.\n",
"mud tug-of-war.\n",
"masters canoe jousting.\n",
"pie-throwing festival.\n"
}; 

int main()
{
	int age;
	cout << "Enter your age in years: ";
	cin >> age;
	int index;
	if (age > 17 && age < 35)
		index = 0;
	else if (age >= 35&& age< 50)
		index=1;
	else if (age >= 50 && age < 65)
		index = 2;
	else
		index = 3;

	cout << "You qualify for the " << qualify[index];
	return 0;
 } 

4.逻辑NOT运算符:!

!运算符将它后面的表达式的真值取反。如果 expression为true,则expression是false;如果expression为false,则!expression是true。更准确地说,如果expression为true或非零,则!expression为false。

#include <iostream>
#include <climits>
using namespace std;
bool is_int (double) ;
int main()
{
	double num;
	cout << "Yo, dude! Enter an integer value: ";
	cin >> num;
	while (!is_int (num))
	{
		cout << "Out of range -- please try again: ";
		cin >> num;
	}
	int val = int (num) ;
	cout << "You've entered the integer " << val << "\nBye\n";
	return 0;
 } 
bool is_int (double x)
{
	if (x <= INT_MAX && x >= INT_MIN)
		return true;
	else
		return false;
}

可以使用long long来替代double,只要其取值范围比int大就好。

5.逻辑运算符细节

C++逻辑OR和逻辑AND运算符的优先级都低于关系运算符。这意味着下面的表达式

x> 5 && x < 10

将被解释为:

(x > 5) && (x < 10)

另一方面,!运算符的优先级高于所有的关系运算符和算术运算符。因此,要对表达式求反,必须用括号将其括起。逻辑AND运算符的优先级高于逻辑OR运算符。虽然C++运算符的优先级规则常可能不使用括号便可以编写复合比较的语句,但最简单的方法还是用括号将测试进行分组,而不管是否需要括号。这样代码容易阅读,避免读者查看不常使用的优先级规则,并减少由于没有准确记住所使用的规则而出错的可能性。C++确保程序从左向右进行计算逻辑表达式,并在知道答案后立刻停止。

6.其他表达方式

并不是所有的键盘都提供了用作逻辑运算符的符号,因此C++标准提供了另一种表示方式。标识符 and、or和not都是C++保留字,这意味着不能将它们用作变量名等。它们不是关键字,因为它们都是已有语言特性的另一种表示方式。另外,它们并不是C语言中的保留字,但C语言程序可以将它们用作运算符,只要在程序中包含了头文件iso646.h。C++不要求使用头文件。

三、字符函数库cctype

C++从C语言继承了一个与字符相关的、非常方便的函数软件包,它可以简化诸如确定字符是否为大写字母、数字、标点符号等工作,这些函数的原型是在头文件cctype中定义的。这些函数的返回类型为int,而不是bool,但通常bool转换能够将它们视为bool类型。

使用这些函数比使用AND和OR运算符更方便。例如,使用AND和OR来测试字符ch是不是字母字符,可以直接使用isalpha()。isalpha()不仅更容易使用,而且更通用。AND/OR格式假设A-Z的字符编码是连续的,其他字符的编码不在这个范围内。这种假设对于ASCII码来说是成立的,但通常并非总是如此。

#include <iostream>
#include <cctype>
using namespace std;

int main()
{
	cout << "Enter text for analysis, and type @"
		" to terminate input.\n";
	char ch;
	int whitespace = 0;
	int digits = 0;
	int chars = 0;
	int punct = 0;
	int others=0;
	cin.get (ch) ;
	while (ch != '@')
	{
		if (isalpha (ch) )
			chars++;
		else if (isspace(ch))
			whitespace++;
		else if (isdigit (ch))
			digits++;
		else if (ispunct (ch) )
			punct++;
		else
			others++;
		cin.get (ch);
	}
	cout << chars << " letters, "
		<< whitespace << " whitespace,"
		<< digits << " digits, "
		<< punct << " punctuations,"
		<< others << " others. \n";
	return 0;
 } 

四、?运算符

C++有一个常被用来代替if else语句的运算符,这个运算符被称为条件运算符(?),它是C++中唯一个需要3个操作数的运算符。该运算符的通用格式如下:

expression1?expression2:expression3

如果expression1为 true,则整个条件表达式的值为expression2的值;否则,整个表达式的值为expression3的值。

#include <iostream>
using namespace std;

int main()
{
	int a, b;
	cout << "Enter two integers: ";
	cin >> a >> b;
	cout << "The larger of " << a << " and " << b;
	int c = a >b?a : b; // c= a if a >b, else c = b
	cout << " is " << c << endl;
	return 0;
 } 

与if else序列相比,条件运算符更简洁。这两种方法之间的区别是,条件运算符生成一个表达式,因此是一个值,可以将其赋给变量或将其放到一个更大的表达式中。条件运算符格式简洁、语法奇特、外观与众不同,因此在欣赏这些特点的程序员中广受欢迎。其中一个技巧是将条件表达式嵌套在另一个条件表达式中。

五、switch语句

switch语句的通用格式:

switch (integer-expression)

{

        case label1: statement (s)
        case label2: statement (s)

        ......

        default : statement (s)

}

C++的switch语句就像指路牌,告诉计算机接下来应执行哪行代码。执行到switch语句时,程序将跳到使用 integer-expression的值标记的那一行。例如,如果-integer-expression的值为4,则程序将执行标签为case4那一行。integer-expression必须是一个结果为整数值的表达式。另外,每个标签都必须是整数常量表达式。最常见的标签是int或char常量(如1或‘q'),也可以是枚举量。如果integer-expression不与任何标签匹配,则程序将跳到标签为default的那一行。default标签是可选的;如果被省略,而又没有匹配的标签,则程序将跳到switch后面的语句处执行。

C+中的case标签只是行标签,而不是选项之间的界线。也是说,程序跳到switch中特定代码行后;将依次执行之后的所有语句,除非有明确的其他指示。程序不会在执行到下一个case处自动停止,要使程序执行完一组特定语句后停止,必须使用break语句。这将导致程序跳到switch后面的语句处执行。

#include <iostream>
using namespace std;
void showmenu(); 
void report ();
void comfort ();
int main()
{
	showmenu(); 
	int choice;
	cin >> choice;
	while (choice != 5)
	{
		switch(choice)
		{
			case 1:cout << "\a\n";
					break;
			case 2:report () ;
					break;
			case 3:cout << "The boss was in all day. \n";
					break;
			case 4:comfort ();
					break;
			default :cout << "That's not a choice.\n";
		}
		showmenu () ;
		cin >> choice;
	}
	cout << "Bye!\n";
	return 0;
 } 
void showmenu ()
{
	cout << "Please enter 1, 2, 3, 4, or 5:\n"
		"1) alarm			2) report\n"
		"3) alibi			4) comfort\n"
		"5) quit\n";
}
void report ()
{
	cout << "It's been an excellent week for business. \n"
	"Sales are up 120%. Expenses are down 35%. \n";
}

void comfort ()
{
	cout << "Your employees think you are the finest CEO\n"
	"in the industry. The board of directors think\n"
	"you are the finest CEO in the industry.\n";
}

1.用枚举量作为标签

通常,cin无法识别枚举类型(它不知道程序员是如何定义它们的),因此一般程序要求用户选择选项时输入一个整数。当switch语句将int值和枚举量标签进行比较时,将枚举量提升为int。另外,在while循环测试条件中,也会将枚举量提升为int类型。

#include <iostream>
using namespace std;
enum color {red, orange, yellow, green, blue, violet, indigo};
int main()
{
	cout << "Enter color code(0-6) : ";
	int Color;
	cin >> Color;
	while (Color >= red && Color <= indigo)
	{
		switch (Color)
		{
			case red:cout<<"Her lips were red.\n"; break;
			case orange:cout<<"Her lips were orange.\n"; break;
			case yellow:cout<<"Her lips were yellow.\n"; break;
			case green:cout<<"Her lips were green.\n"; break;
			case blue:cout<<"Her lips were blue.\n"; break;
			case violet:cout<<"Her lips were violet.\n"; break;
			case indigo:cout<<"Her lips were indigo.\n"; break;
		}
		cout << "Enter color code(0-6) : ";
		cin >> Color;
	}
	cout<<"Bye\n";
	return 0;
 } 

2.switch和if else

switch 语句和if else语句都允许程序从选项中进行选择。相比之下,if else更通用。例如,if else可以处理取值范围。

然而,switch并不是为处理取值范围而设计的。switch语句中的每一个case 标签都必须是一个单独的值。另外,这个值必须是整数(包括char),因此switch无法处理浮点测试。另外case标签值还必须是常量。如果选项涉及取值范围、浮点测试或两个变量的比较,则应使用if else语句。如果所有的选项都可以使用整数常量来标识,则可以使用switch语句或if else语句。由于switch语句是专门为这种情况设计的,因此,如果选项超过两个,则就代码长度和执行速度而言,switch语句的效率更高。如果既可以使用if else语句,也可以使用switch语句,则当选项不少于3个时,应使用switch语句。

六、break和continue语句

break 和 continue语句都使程序能够跳过部分代码。可以在switch语句或任何循环中使用break语句,使程序跳到 switch或循环后面的语句处执行。continue语句用于循环中,让程序跳过循环体中余下的代码,并开始新一轮循环。

#include <iostream>
using namespace std;
const int ArSize = 80;
int main()
{
	char line [ArSize];
	int spaces = 0;
	cout << "Enter a line of text:\n";
	cin.get(line, ArSize);
	cout << "Complete line: \n" << line << endl;
	cout << "Line through first period: \n";
	for (int i = 0; line[i] != '\0'; i++)
	{
		cout<<line[i]; 
		if (line[i] == '.') // quit if it's a period
			break;
		if (line[i] != ' ') // skip rest of loop
			continue;
		spaces++;
	}
	cout << "\n" << spaces << " spaces\n";
	cout << "Done.\n";
	return 0;
 } 

和C语言一样,C++也有goto语句。

goto label;

......

label: statement;

在大多数情况下,使用goto语句不好,而应使用结构化控制语句(如if else、switch、continue 等)来控制程序的流程。

七、读取数字的循环

如果声明了一个int,而用户输入了一个字符。那么发生这种类型不匹配的情况时,将发生4种情况:

  • n的值保持不变;
  • 不匹配的输入将被留在输入队列中;
  • cin对象中的一个错误标记被设置;
  • 对cin方法的调用将返回false(如果被转换为bool类型)。

方法返回false意味着可以用非数字输入来结束读取数字的循环。非数字输入设置错误标记意味着必须重置该标记,程序才能继续读取输入。clear()方法重置错误输入标记,同时也重置文件尾。输入错误和EOF都将导致cin返回false。

#include <iostream>
using namespace std;
const int Max = 5;
int main()
{
	double fish [Max];
	cout << "Please enter the weights of your_fish.\n";
	cout << "You may enter up to " << Max
		<< " fish <q_to terminate>.\n";
	cout << "fish #1: ";
	int i= 0;
	while (i < Max && cin>> fish[i]) 
	{
		if (++i < Max)
		cout << "fish #" <<i+1 << ": ";
	}
	double total = 0.0;
	for (int j = 0; j <i; j++)
		total += fish[j];
	if (i == 0)
		cout << "No fish\n";
	else
		cout << total / i << " = average weight of "
			<< i << " fish\n";
	cout << "Done. \n";
	return 0;
 } 

当用户输入的不是数字时,该程序将不再读取输入。如果用户输入非数字输入,程序将拒绝,并要求用户继续输入数字。可以看到,可以使用cin输入表达式的值来检测输入是不是数字。程序发现用户输入了错误内容时,应采取3个步骤:

  1. 重置cin以接受新的输入。
  2. 删除错误输入。
  3. 提示用户再输入。

程序必须先重置cin,然后才能删除错误输入。

#include <iostream>
using namespace std;
const int Max = 5;
int main()
{
	int golf [Max];
	cout << "Please enter your golf scores.\n";
	cout << "You must enter " << Max << " rounds. \n";
	int i;
	for (i = 0; i < Max; i++)
	{
		cout << "round #" << i+1 << ": ";
		while (! (cin >> golf [i])) 
		{
			cin.clear();
			while (cin.get() != '\n')
				continue;
			cout << "Please enter a number: ";
		}
	}
	double total = 0.0;
	for (i = 0; i < Max; i++)
	{
		total += golf [i];
	}
	cout << total / Max << " = average score "
		<< Max << " rounds\n";
	return 0;
 } 

八、简单文件输入/输出

1.文本I/O和文本文件

使用cin进行输入时,程序将输入视为一系列的字节,其中每个字节都被解释为字符编码。不管目标数据类型是什么,输入一开始都是字符数据——文本数据。然后,cin对象负责将文本转换为其他类型。

如果输入行为

12.2 13.5

  1. 使用char数据类型:char ch; cin>>ch;
    输入行中的第一个字符被赋给ch。在这里,第一个字符是数字1,其字符编码(二进制)被存储在变量ch中。输入和目标变量都是字符,因此不需要进行转换。注意,这里存储的不是数值1,而是字符1的编码。执行上述输入语句后,输入队列中的下一个字符为字符2,下一个输入操作将对其进行处理。
  2. 使用int类型:int n;cin>>n;
    在这种情况下,cin将不断读取,直到遇到非数字字符。也就是说,它将读取1和2,这样句点将成为输入队列中的下一个字符。cin通过计算发现,这两个字符对应数值12,因此将12的二进制编码复制到变量n中。
  3. 使用double类型:double x;cin>>x;
    在这种情况下,cin将不断读取,直到遇到第一个不属于浮点数的字符。也就是说,cin读取1、2、句点和2,使得空格成为输入队列中的下一个字符。cin通过算发现,这四个字符对应于数值12.2,因此将12.2的二进制编码(浮点格式)复制到变量x中。
  4. 使用char数组:char word[50];cin>>word;
    在这种情况下,cin将不断读取,直到遇到空白字符。也就是说,它读取1、2、句点和2,使得空格成为输入队列中的下一个字符。然后,cin将这4个字符的字符编码存储到数组word中,并在末尾加上一个
  5. 另一种使用char数组的形式:char word[50];cin.getline(word,50);
    在这种情况下,cin将不断读取,直到遇到换行符(当前示例)。所有字符都将被存储到数组 word 中,并在末尾加上一个空字符。换行符被丢弃,输入队列中的下一个字符是下一行中的第一个字符。这里不需要进行任何转换。

对于输出,将执行相反的转换。即整数被转换为数字字符序列,浮点数被转换为数字字符和其他字符组成的字符序列(如284.53或-1.58E+06)。字符数据不需要做任何转换。

这里的要点是,输入一开始为文本。因此,控制台输入的文件版本是文本文件,即每个字节都存储了个字符编码的文件。并非所有的文件都是文本文件,例如,数据库和电子表格以数值格式(即二进制整数或浮点格式)来存储数值数据。另外,字处理文件中可能包含文本信息,但也可能包含用于描述格式、字体、打印机等的非文本数据。

要创建文本文件,用于提供输入,可使用文本编译器,也可以使用字处理程序来创建,但必须将文件保存为文本格式。IDE中的源代码编辑器生成的也是文本文件,事实上,源代码文件就属于文本文件。同样,可以使用文本编辑器来查看通过文本输出创建的文件。

2.写入到文本文件中

将用于控制台输出的ostream对象和用于文件输入的ftream进行对比。

控制台输出的特点:

  1. 必须包含头文件iostream。
  2. 头文件iostream定义了一个用处理输出的ostream类。
  3. 头文件iostream声明了一个名为cout的ostream 变量(对象)。
  4. 必须指明名称空间 std;例如,为引用元素cout 和 endl,必须使用编译指令 using或前缀std。
  5. 可以结合使用cin和运算符>>来读取各种类型的数据。
  6. 可以使用cin和get()方法来读取一个字符,使用cin和getline()来读取一行字符。
  7. 可以结合使用cin和eof()、fail()方法来判断输入是否成功。
  8. 对象 cin本身被用作测试条件时,如果最后一个读取操作成功,它将被转换为布尔值 true,否则被转换为 false。

文件输出的特点:

  1. 必须包含文件fstream。
  2. 头文件fstream定义了一个用于处理输入的ifstream类。
  3. 需要声明一个或多个ifstream变量(对象),并以自己喜欢的方式对其进行命名,条件是遵守常用的命名规则。
  4. 必须指明名称空间std;例如,为引用元素ifstream,必须使用编译指令using 或前缀std:: 。
  5. 需要将ifstream对象与文件关联起来。为此,方法之一是使用open()方法。
  6. 使用完文件后,应使用close()方法将其关闭。
  7. 可结合使用ifstream对象和运算符>>来读取各种类型的数据。
  8. 可以使用ifstream对象和get()方法来读取一个字符,使用ifstream对象和getline()来读取一行字符。
  9. 可以结合使用ifstream和eof()、fail()等方法来判断输入是否成功。
  10. ifstream对象本身被用作测试条件时,如果最后一个读取操作成功,它将被转换为布尔值true,否则被转换为false。

注意,虽然头文件iostream提供了一个预先定义好的名为cin的istream对象,但必须声明自己的ifstream 对象,为其命名,并将其同文件关联起来。

ifstream inFile;
ifstream fin;

inFile.open("bowling.txt");
char filename[50];
cin>> filename;
fin.open(filename);

注意,方法 open()接受一个C-风格字符串作为参数,这可以是一个字面字符串,也可以是存储在数组中的字符串。

double wt;
inFile >> wt;
char line [81];
fin.getline(Iine, 81);

声明一个ifstream对象并将其同文件关联起来后,便可以像使用cin那样使用它。所有可用于cin的操作和方法都可用于ifstream对象。如果试图打开一个不存在的文件用于输入,这种错误将导致后面使用ifstream 对象进行输入时失败。检查文件是否被成功打开的首先方法是使用方法is_open()。

inFile.open("bowling.txt");
if (!inFile.is_open())

{

        exit (EXIT_FAILURE);

}

如果文件被成功地打开,方法is_open()将返回true;因此如果文件没有被打开,表达式!inFile.isopen()将为true。函数exit()的原型是在头文件cstdlib中定义的,在该头文件中,还定义了一个用于同操作系统通信的参数值EXIT_FAILURE。函数exit()终止程序。

方法is_open()是C++中相对较新的内容。如果编译器不支持它,可使用较老的方法good()来代替。方法good()在检查可能存在的问题,没有is_open()那么广泛。

#include <iostream>
#include <fstream>
#include <cstdlib>
using namespace std; 
const int SIZE = 60;
int main()
{
	char filename [SIZE];
	ifstream inFile;
	cout << "Enter name of data file: ";
	cin.getline(filename, SIZE);
	inFile.open(filename); // associate inFile with a file
	if (!inFile.is_open())
	{
		cout << "Could not open the file " << filename << endl;
		cout << "Program terminating.\n";
		exit (EXIT_FAILURE);
	}
	double value;
	double sum = 0.0;
	int count = 0;
	inFile >> value;
	while (inFile.good())
	{
		++count;
		sum += value;
		inFile >> value;
	}
	if (inFile.eof ())
		cout << "End of file reached.\n";
	else if (inFile.fail())
		cout << "Input terminated by data mismatch.\n";
	else
		cout << "Input terminated for unknown reason. \n";
	if (count == 0)
		cout << "No data processed. \n";
	else
	{
		cout << "Items read: " << count << endl;
		cout << "Sum: " << sum << endl;
		cout << "Average: " << sum / count << endl;
	}
	inFile.close();
	return 0;
}

Windows 文本文件的每行都以回车字符和换行符结尾;通常情况下,C++在读取文件时将这两个字符转换为换行符,并在写入文件时执行相反的转换。有些文本编辑器不会自动在最后一行末尾加上换行符。因此,如果使用的是这种编辑器,在输入最后的文本后按下回车键,然后再保存文件。

首先,程序读取文件时不应超过EOF。如果最后一次读取数据时遇到EOF,方法eof()将返回true。其次,程序可能遇到类型不匹配的情况。例如,程序期望文件中只包含数字。如果最后一次读取操作中发生了类型不匹配的情况,方法fail()将返回true(如果遇到了EOF,该方法也将返回true)。最后,可能出现意外的问题,如文件受损或硬件故障。如果最后一次读取文件时发生了这样的问题,方法bad()将返回true。不需要分别检查这些情况,一种更简单的方法是使用good()方法,该方法在没有发生任何错误时返回true。

while (inFile.good())

{

        ......

}

或者

if (inFile.eof ())
        cout << "End of file reached.\n"
else if (inFile.fail ())
        cout << "Input terminated by data mismatch.\n";
else
        cout << "Input. terminated for unknown-reason. \n";

方法good()指出最后一次读取输入的操作是否成功,这一点至关重要。这意味着应该在执行读取输入的操作后,立刻应用这种测试。为此,一种标准方法是,在循环之前(首次执行循环测试前)放置一条输入语句,并在循环的末尾“(下次执行循环测试之前)放置另一条输入语句:

inFile >> value;
while (inFile.good())

{

        inFile >> value;

}

表达式inFile>>value 的结果为inFile,而在需要一个bool值的情况下,inFile的结果为inFile.good(),即true或false。因此,可以将两条输入语句用一条用作循环测试的输入语句代替。

while (inFile >> value)

{

 ......       

}

  • 11
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值