[C++ primer] 第三章习题答案
3.13.23.33.43.53.63.83.93.103.113.123.133.163.173.183.193.243.263.273.283.293.303.313.333.343.353.363.373.383.393.403.413.423.43
3.1
使用using namespace std;即可
3.2
一次读入一行:使用getline
#include <iostream>
#include <string>
using namespace std
;
int main()
{
string line
;
while (getline(cin
, line
))
{
cout
<< line
<< endl
;
}
}
一次读入一个词:使用cin
#include <iostream>
#include <string>
using namespace std
;
int main()
{
string word
;
while (cin
>> word
)
{
cout
<< word
<< endl
;
}
}
3.3
使用string类的输入运算符时,string对象会自动忽略开头的空白(空格符、换行符、制表符等)并从第一个真正的字符开始读起,直到遇到下一个空白为止。 使用getline函数时,函数从给定的输入流中读入内容,直到遇到换行符为止(换行符也读进来了),然后将所读内容存入到string对象中去(不存换行符)
3.4
//没有判断相等的情况,默认str1和str2不等长,不相等
#include <iostream>
#include <string>
using namespace std
;
int main()
{
string str1
, str2
;
cin
>> str1
>> str2
;
if(str1
!= str2
)
{
cout
<< (str1
> str2
? str1
: str2
) << endl
;
}
cout
<< (str1
.size() > str2
.size() ? str1
.size() : str2
.size()) << endl
;
}
3.5
#include <iostream>
#include <string>
using namespace std
;
int main()
{
string str
;
string res1
= "";
string res2
= "";
while (getline(cin
, str
))
{
res1
+= str
;
res2
+= str
+ " ";
cout
<< "res1 = " << res1
<< endl
;
cout
<< "res2 = " << res2
<< endl
;
}
}
3.6
#include <iostream>
#include <string>
using namespace std
;
int main()
{
string str
;
cin
>> str
;
for (char &i
: str
)
{
i
= 'X';
}
cout
<< str
<< endl
;
}
3.8
已知循环次数,用for循环更加简洁
3.9
不合法,string类型的下标必须大于等于0而小于等于.size() 使用超出此范围的下标将引发不可预知的结果,使用下标访问空string也会引发不可预知的结果
3.10
#include <iostream>
#include <string>
#include <cctype>
using namespace std
;
int main()
{
string str
;
string res
= "";
cin
>> str
;
for (char i
: str
)
{
if (!ispunct(i
))
{
res
+= i
;
}
}
cout
<< res
<< endl
;
}
3.11
不合法,设置一个auto类型的引用时,初始值中的顶层const依旧保留,c的类型为const string&。 因此,如果, 在for循环中要改变c的值,则语句不合法。
3.12
(a)正确 (b)不正确,类型不一致 (c)正确
3.13
(a)空vector (b)十个元素,均为0 (c)十个元素,均为42 (d)一个元素,10 (e)两个元素, 10, 42 (f)十个默认初始化的元素 (g)十个元素,均为hi
3.16
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
vector
<int> v1
;
vector
<int> v2(10);
vector
<int> v3(10, 42);
vector
<int> v4
{ 10 };
vector
<int> v5
{ 10, 42 };
vector
<string
> v6
{ 10 };
vector
<string
> v7
{ 10, "hi" };
vector
<int>::iterator iter
;
for (iter
= v3
.begin(); iter
!= v3
.end(); iter
++)
{
cout
<< *iter
<< endl
;
}
}
3.17
c = toupper(c);
3.18
不合法,ivec为空,不包含任何元素,不能通过下标去访问元素。应改为 ivec.push_back(42);
3.19
vector
<int> temp1(10, 42);
vector
<int> temp2(temp1
);
vector
<int> temp3
= temp1
;
vector
<int> temp4
= {42, 42, 42, 42, 42, 42, 42, 42, 42, 42}
3.24
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
vector
<int> text
;
for (int i
= 0; i
< 10; i
++)
{
text
.push_back(i
);
}
vector
<int>::iterator iter
;
for (iter
= text
.begin(); iter
!= text
.end() - 1; iter
++)
{
cout
<< *iter
+ *(iter
+ 1) << endl
;
}
vector
<int>::iterator iter2
;
for (iter
= text
.begin(), iter2
= text
.end(); iter
!= iter2
; iter
++)
{
iter2
--;
cout
<< *iter
+ *iter2
<< endl
;
}
}
3.26
因为end指向最后一个元素的下一个位置。
3.27
(a)非法,buf_size不是常量 (b)合法 (c)非法,函数返回值不是常量 (d)非法,没有空间可以存储空字符
以下解释来自:https://blog.csdn.net/misayaaaaa/article/details/53349998 理解复杂数组的声明(难点)
不可以将数组的内容拷贝给其他数组当作初始值,也不能用数组为其他数组赋值。
int a
[3] = {0,1,3};
int a1
[] = a
;
a2
= a
;
复杂数组声明的理解
int *a
[10];
int &a
[10];
int (*a
)[10];
int (&a
)[10];
int *(&a
)[10];
理解方法:从数组的名字开始,由内向外顺序读取,先左后右,左边为类型。
3.28
string不是内置的数据类型,int是内置的数据类型 sa为空数组 ia中有10个0 sa2为空数组 ia2中有10个整数,由于在函数体内,内容未知
3.29
长度不可变,一旦确定长度,不可以再更改长度
3.30
下标应该是0-array_size - 1
3.31
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
int a
[10] = { 0,1,2,3,4,5,6,7,8,9 };
int b
[10];
for (int i
= 0; i
< 10; i
++)
{
b
[i
] = a
[i
];
cout
<< b
[i
] << endl
;
}
vector
<int> c
;
for (int i
= 0; i
< 10; i
++)
{
c
.push_back(i
);
}
vector
<int> d
= c
;
}
3.33
不初始化scores,则其中内容未知,可能为空,也可能有别的数据。(因为scores在函数体内)
3.34
p1 = p2 ,因为p1和p2指向同一地址,所以p1地址不变。 当p1和p2指向不同的数组,则语句非法。
3.35
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
int a
[10] = { 0,1,2,3,4,5,6,7,8,9 };
int *p
= a
;
for (int i
= 0; i
< 10; i
++)
{
p
[i
] = 0;
cout
<< a
[i
] << endl
;
}
}
3.36
比较数组相等,先比较数组的大小(sizeof(A)),再比较数组的每个元素。 比较vector相等,可以直接比较
3.37
C风格字符串以空字符结束。则传入此类函数的指针必须指向以空字符作为结束的数组。
将ca的每个元素都输出出来。但由于s初始化时,并未加‘\0’,因此其长度未知,while循环会一直继续知道遇见’\0’。输出“hello+未知字符”。
3.38
两个指针相加,相当于两个地址值相加.因此毫无意义
3.39
C++风格的字符串比较是字符串本身的比较
C风格的字符串比较是字符串首地址的比较
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
string str1
= "hello world";
string str2
= "hello world";
if (str1
== str2
) {
cout
<< str1
<< " is equal with " << str2
<< endl
;
}
else {
cout
<< str1
<< " is not equal with " << str2
<< endl
;
}
char s1
[] = { 'c', '+', '+', '\0' };
char s2
[] = { 'c', '+', '+', '\0' };
int result
= strcmp(s1
, s2
);
if (0 == result
) {
cout
<< "s1 is equal with s2!" << endl
;
}
else {
cout
<< "s1 is not equal with s2!" << endl
;
}
}
3.40
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
char str1
[20] = "hello world";
char str2
[20] = "hello world";
char str3
[50];
strcpy(str3
, str1
);
strcat(str3
, " ");
strcpy(str3
, str2
);
}
3.41
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
int a
[10] = { 0,1,2,3,4,5,6,7,8,9 };
vector
<int> temp(a
, a
+ 10);
for (int i
= 0; i
< temp
.size(); i
++)
{
cout
<< temp
[i
] << endl
;
}
}
3.42
逐个拷贝
3.43
#include <iostream>
#include <string>
#include <cctype>
#include <vector>
using namespace std
;
int main()
{
int ia
[3][4] = {
{0, 1, 2, 3},
{4, 5, 6, 7},
{8, 9, 10, 11}
};
for (int (&row
)[4] : ia
)
{
for (int col
: row
)
{
cout
<< col
<< endl
;
}
}
for (int i
= 0; i
< 3; i
++)
{
for (int j
= 0; j
< 4; j
++)
{
cout
<< ia
[i
][j
] << endl
;
}
}
for (int (*p
)[4] = ia
; p
!= ia
+ 3; p
++)
{
for (int *q
= *p
; q
!= *p
+ 4; q
++)
{
cout
<< *q
<< endl
;
}
}
}