日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

第 2 章

發(fā)布時(shí)間:2025/7/14 编程问答 15 豆豆
生活随笔 收集整理的這篇文章主要介紹了 第 2 章 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

2.1

int、long、long long 和 short 表示整型類型,C++語(yǔ)言規(guī)定它們表示數(shù)的范圍 short \(\leq\) int \(\leq\) long \(\leq\) long long。其中,數(shù)據(jù)類型 long long 是在 C++11 中新定義的;

除去布爾型和擴(kuò)展的字符型之外,其它整型可以劃分為帶符號(hào)的(signed)無符號(hào)的(unsigned)兩種。帶符號(hào)類型可以表示正數(shù)、負(fù)數(shù)和 0,無符號(hào)類型則僅能表示大于等于 0 的值。類型 int、short、long 和 long long 都是帶符號(hào)的,通過在這些類型名前添加 unsigned 就可以得到無符號(hào)類型,例如 unsigned long。類型 unsigned int 可以縮寫為 unsigned;

float 和 double 用于表示浮點(diǎn)數(shù),其中,float 表示單精度浮點(diǎn)數(shù),double 表示雙精度浮點(diǎn)數(shù)。執(zhí)行浮點(diǎn)數(shù)運(yùn)算選用 double,這是因?yàn)?float 通常精度不夠而且雙精度浮點(diǎn)數(shù)和單精度浮點(diǎn)數(shù)的計(jì)算代價(jià)相差無幾。事實(shí)上,對(duì)于某些機(jī)器來說,雙精度運(yùn)算甚至比單精度還快。long double 提供的精度在一般情況下是沒有必要的,況且它帶來的運(yùn)算時(shí)消耗也不容忽視。

附:單精度與雙精度是什么意思,有什么區(qū)別?

2.2

利率(rat):float,本金(principal):long long,付款(payment):long long。

利率一般是小數(shù)點(diǎn)后保留四位有效數(shù)字,float 合適;本金和付款使用最大的帶符號(hào)整型表示。

2.3

main.cpp

#include <iostream>int main() {std::cout << sizeof(unsigned) << std::endl;std::cout << sizeof(int) << std::endl;std::cout << "**************************" << std::endl;unsigned u = 10, u2 = 42;std::cout << u2 - u << std::endl;std::cout << u - u2 << std::endl;std::cout << "**************************" << std::endl;int i = 10, i2 = 42;std::cout << i2 - i << std::endl;std::cout << i - i2 << std::endl;std::cout << i - u << std::endl;std::cout << u - i << std::endl;return 0; } 4 4 ************************** 32 4294967264 ************************** 32 -32 0 0Process finished with exit code 0 unsigned int 占 4 字節(jié) int 占 4 字節(jié) ************************** u2 - u = 42 - 10 = 32 u - u2 = 10 - 42 = unsigned(-32) = 4294967264 分析一: 32 的二進(jìn)制表示為 0000 0000 0000 0000 0000 0000 0010 0000 -32 的二進(jìn)制補(bǔ)碼表示為 1111 1111 1111 1111 1111 1111 1110 0000 也就是說 -32 的十六進(jìn)制表示為 FFFF FFE0 若將 FFFF FFE0 轉(zhuǎn)換為 unsigned int 類型,則高位的符號(hào)位全部成為了數(shù)值位,FFFF FFE0 按無符號(hào)數(shù)轉(zhuǎn)換成十進(jìn)制數(shù)為 4294967264。 分析二: 把負(fù)數(shù)轉(zhuǎn)換成無符號(hào)數(shù)類似于直接給無符號(hào)數(shù)賦一個(gè)負(fù)值,結(jié)果等于這個(gè)負(fù)數(shù)加上無符號(hào)數(shù)的模。 unsigned int 占 4 字節(jié),4 字節(jié)的無符號(hào)數(shù)模為 4294967296。 -32 + 4294967296 = 4294967264 ************************** i2 - i = 42 - 10 = 32 i - i2 = 10 - 42 = -32 當(dāng)一個(gè)算術(shù)表達(dá)式中既有無符號(hào)數(shù)又有 int 值時(shí),那個(gè) int 值就會(huì)轉(zhuǎn)換成無符號(hào)數(shù)。 i - u = unsigned(10) - 10 = 0 u - i = 10 - unsigned(10) = 0 分析: 有符號(hào)數(shù) 10 轉(zhuǎn)換成無符號(hào)數(shù) 10,因?yàn)?10 是正數(shù),符號(hào)位為 0,故轉(zhuǎn)換成無符號(hào)數(shù)時(shí),符號(hào)位不會(huì)對(duì)對(duì)應(yīng)無符號(hào)數(shù)產(chǎn)生副作用。Process finished with exit code 0 程序中 return 0 語(yǔ)句的副作用

2.4

請(qǐng)看 2.3

2.5

(a) 'a', L'a', "a", L"a"

字面值數(shù)據(jù)類型
'a'字符字面值,類型是 char
L'a'寬字符字面值,類型是 wchar_t
"a"字符串字面值
L"a"寬字符串字面值

(b) 10, 10u, 10L, 10uL, 012, 0xC

字面值數(shù)據(jù)類型
10整型字面值,類型是 int
10u無符號(hào)整型字面值,類型是 unsigned int
10L整型字面值,類型是 long
10uL無符號(hào)整型字面值,類型是 unsigned long
012八進(jìn)制整型字面值,類型是 int
0xC十六進(jìn)制整型字面值,類型是 int

(c) 3.14, 3.14f, 3.14L

字面值數(shù)據(jù)類型
3.14浮點(diǎn)數(shù)字面值,類型是 double
3.14f浮點(diǎn)數(shù)字面值,類型是 float
3.14L浮點(diǎn)數(shù)字面值,類型是 long double

(d) 10, 10u, 10., 10e-2

字面值數(shù)據(jù)類型
10整型字面值,類型是 int
10u無符號(hào)整型字面值,類型是 unsigned int
10.浮點(diǎn)數(shù)字面值,類型是 double
10e-2浮點(diǎn)數(shù)字面值,類型是 double

2.6

有區(qū)別

int month = 9, day = 7; // 9 和 7 是十進(jìn)制數(shù),正確的賦值 // 以 0 開始表示八進(jìn)制,八進(jìn)制各位范圍是 0 ~ 7,賦值不合法 int month = 09, day = 07;

2.7

字面值數(shù)據(jù)類型
"Who goes with F\145rgus?\012"字符串字面值,包含兩個(gè)八進(jìn)制轉(zhuǎn)義序列
3.14e1L浮點(diǎn)數(shù)字面值,類型是 long double
1024f浮點(diǎn)數(shù)字面值,類型是 float
3.14L浮點(diǎn)數(shù)字面值,類型是 long double

2.8

分別寫了八進(jìn)制和十六進(jìn)制的版本

ASCII

#include <iostream>int main() {std::cout << "-------- Oct --------" << std::endl;std::cout << "\62\115\12";std::cout << "---------------------" << std::endl;std::cout << "\62";std::cout << "\11";std::cout << "\115";std::cout << "\12";std::cout << "-------- Hx ---------" << std::endl;std::cout << "\x32\x4d\xa";std::cout << "---------------------" << std::endl;std::cout << "\x32";std::cout << "\x9";std::cout << "\x4d";std::cout << "\xa";return 0; } // 運(yùn)行結(jié)果 -------- Oct -------- 2M --------------------- 2 M -------- Hx --------- 2M --------------------- 2 MProcess finished with exit code 0

2.9

// (a) // std::cin >> int input_value; // Error: variable must be defined before using for input int input_value; std::cin >> input_value;// (b) // int i = { 3.14 }; // Error: loss information in list initialization double d = { 3.14 }; // OK double d2 = { 3 }; // OK// (c) // double salary = wage = 9999.99; // Error double salary, wage; salary = wage = 9999.99;// (d) int i2 = 3.14; // OK, `i2` is 3

2.10

#include <iostream>std::string global_str; int global_int; int main () {int local_int;std::string local_str;std::cout << "global_str = " << global_str << std::endl;std::cout << "global_int = " << global_int << std::endl;std::cout << "local_str = " << local_str << std::endl;std::cout << "local_int = " << local_int << std::endl;return 0; } // 運(yùn)行結(jié)果 global_str = global_int = 0 local_str = local_int = -406316616Process finished with exit code 0

2.11

extern int ix = 1024; // 定義 int iy; // 聲明并定義 iy extern int iz; // 聲明 iz 而非定義 iz

2.12

int double = 3.14; // 錯(cuò)誤,c++關(guān)鍵字 double 不能作為標(biāo)識(shí)符 int _; // 正確 int catch-22; // 錯(cuò)誤,標(biāo)識(shí)符由數(shù)字、字母和下劃線組成 int 1_or_2 = 1; // 錯(cuò)誤,標(biāo)識(shí)符必須以字母或下劃線開頭 double Double = 3.14; // 正確,標(biāo)識(shí)符長(zhǎng)度沒有限制,大小寫敏感

2.13

程序中 j 的值是 100

2.14

#include <iostream>int main () {int i = 100, sum = 0;for (int i = 0; i != 10; ++i)sum += i;std::cout << i << " " << sum << std::endl;return 0; } // 運(yùn)行結(jié)果 100 45Process finished with exit code 0

2.15

#include <iostream>int main () {// 正確,隱式的將 1.01 轉(zhuǎn)換成 1int ival= 1.01;// 錯(cuò)誤,除 2.4.1 節(jié)(第 55 頁(yè))和 15.2.3 節(jié)(第 534 頁(yè))將// 要介紹的兩種例外情況,引用的類型都要和與之綁定的對(duì)象嚴(yán)格匹// 配。而且,引用只能綁定在對(duì)象上,而不能與字面值或某個(gè)表達(dá)式的// 計(jì)算結(jié)果綁定在一起,相關(guān)原因?qū)⒃?2.4.1 節(jié)詳述int &rval1 = 1.01;// 正確int &rval2 = ival;// 錯(cuò)誤,引用必須被初始化,且初始值必須是一個(gè)對(duì)象int &rval3;return 0; }

2.16

#include <iostream>int main () {int i = 0, &r1 = i;double d = 0, &r2 = d;// 正確r2 = 3.14159;std::cout << r2 << "\n";// 正確,發(fā)送自動(dòng)類型轉(zhuǎn)換r2 = r1;std::cout << r2 << '\n';// 正確,發(fā)送自動(dòng)類型轉(zhuǎn)換i = r2;std::cout << i << std::endl;// 正確,發(fā)送自動(dòng)類型轉(zhuǎn)換r1 = d;std::cout << r1 << std::endl;return 0; }

2.17

#include <iostream>int main () {int i, &ri = i;i = 5;ri = 10;std::cout << i << " " << ri << std::endl;return 0; } // 運(yùn)行結(jié)果 10 10Process finished with exit code 0

2.18

#include <iostream>int main () {int ival = 23, *ip = &ival;std::cout << "ival = " << ival << " " << "*ip = " << *ip << std::endl;*ip = 24;std::cout << "ival = " << ival << " " << "*ip = " << *ip << std::endl;ival = 25;std::cout << "ival = " << ival << " " << "*ip = " << *ip << std::endl;return 0; } // 運(yùn)行結(jié)果 ival = 23 *ip = 23 ival = 24 *ip = 24 ival = 25 *ip = 25Process finished with exit code 0

2.19

引用

引用(reference)為對(duì)象起了另外一個(gè)名字,引用類型引用(refers to)另外一種類型。

int ival = 1024; int &refVal = ival; // refVal 指向 ival(是 ival 的另一個(gè)名字) int &refVal2; // 報(bào)錯(cuò):引用必須被初始化 int &refVal4 = 10; // 錯(cuò)誤:引用類型的初始值必須是一個(gè)對(duì)象 // 除特殊情況,其他所有引用的類型都要和與之綁定的對(duì)象嚴(yán)格匹配 double dval = 3.14; int &refVal5 = dval; // 錯(cuò)誤:此處引用類型的初始值必須是 int 型對(duì)象

指針

指針(pointer)是"指向(point to)"另外一種類型的復(fù)合類型。與引用類似,指針也實(shí)現(xiàn)了對(duì)其他對(duì)象的間接訪問。然而指針與引用相比又有很多不同點(diǎn)。

  • 指針本身就是一個(gè)對(duì)象,允許對(duì)指針賦值和拷貝,而且在指針的生命周期內(nèi)它可以先后指向幾個(gè)不同的對(duì)象;

  • 指針無須在定義時(shí)賦初值;

  • 因?yàn)橐貌皇菍?duì)象,沒有實(shí)際地址,所以不能定義指向引用的指針;

  • 除特殊情況,其他所有指針的類型都要和它所指向的對(duì)象嚴(yán)格匹配;

  • 空指針的定義方法:

    int *p1 = nullptr; // C++11 新標(biāo)準(zhǔn)引人的方法,推薦使用 int *p2 = 0; // 直接將 p2 初始化為字面值常量 0 // 需要首先 #include cstdlib int *p3 = NULL;

    三種定義空指針的方法等價(jià),推薦使用第一種。

  • 雖然指針無須在定義時(shí)賦初值,但是記得初始化所有指針。如果實(shí)在不清楚指針應(yīng)該指向何處,就把它初始化為 nullptr 或者 0,這樣程序就能檢測(cè)并知道它沒有指向任何具體的對(duì)象了。使用未經(jīng)初始化的指針是引發(fā)運(yùn)行時(shí)錯(cuò)誤的一大原因。

2.20

\(i\) 的值修改為 \(i^2\)

#include <iostream>int main () {int i = 42;int *p1 = &i;*p1 = *p1 * *p1;std::cout << "i = " << i << " " << "*p1 = " << *p1;return 0; } // 運(yùn)行結(jié)果 i = 1764 *p1 = 1764 Process finished with exit code 0

2.21

int i = 0; double *dp = &i; // 錯(cuò)誤,指針的類型都要和它所指向的對(duì)象嚴(yán)格匹配 int *ip = i; // 錯(cuò)誤,忘記取地址符 & int *p = &i; // 正確

2.22

if (p) means if the pointer p is not null.

if (*p) means if the object pointed by the pointer is not false (which means the object is not null or zero etc.).

#include <iostream>int main () {int i = 42;int *p = &i;std::cout << "p = " << p << " " << "*p = " << *p << std::endl;if (p)std::cout << "true" << std::endl;elsestd::cout << "false" << std::endl;if (*p)std::cout << "true" << std::endl;elsestd::cout << "false" << std::endl;i = 0;p = &i;std::cout << "p = " << p << " " << "*p = " << *p << std::endl;if (p)std::cout << "true" << std::endl;elsestd::cout << "false" << std::endl;if (*p)std::cout << "true" << std::endl;elsestd::cout << "false" << std::endl;return 0; } // 運(yùn)行結(jié)果 p = 0x7ffee92f3818 *p = 42 true true p = 0x7ffee92f3818 *p = 0 true falseProcess finished with exit code 0

2.23

No, you can't. Because it would be expensive to maintain meta data about what constitutes a valid pointer and what doesn't, and in C++ you don't pay for what you don't want.

See answer here.

However, a smart pointer can be used to tell if it points to a valid object.

注:此題解答來自

2.24

int main() {int i = 42;void *p = &i; // OK, a `void *` pointer can point to any type//long *lp = &i; // Error, a `long *` pointer can not point to `int *`return 0; }

2.25

#include <iostream>int main() {{int* ip, i, &r = i; // `ip` is `int *`, `i` is `int`, `r` is `int &`std::cout << "(a)" << std::endl;std::cout << "ip\t" << typeid(ip).name() << std::endl;std::cout << "i\t" << typeid(i).name() << std::endl;std::cout << "r\t" << typeid(r).name() << std::endl;// Note that `typeid` will lose the `const` qualifier and reference}{int i, *ip = 0; // `i` is `int`, `ip` is `int *`std::cout << "(b)" << std::endl;std::cout << "i\t" << typeid(i).name() << std::endl;std::cout << "ip\t" << typeid(ip).name() << std::endl;}{int* ip, ip2; // `ip` is `int *`, `ip2` is `int`std::cout << "(c)" << std::endl;std::cout << "ip\t" << typeid(ip).name() << std::endl;std::cout << "ip2\t" << typeid(ip2).name() << std::endl;}return 0; } // 運(yùn)行結(jié)果 (a) ip Pi i i r i (b) i i ip Pi (c) ip Pi ip2 iProcess finished with exit code 0

注:

Understanding the output of typeid().name()

std::type_info::name

2.26

本題所有語(yǔ)句應(yīng)該被看作是順序執(zhí)行的,即形如:

const int buf; int cnt = 0; const int sz = cnt; ++cnt; ++sz;

(a)是非法的,const 對(duì)象一旦創(chuàng)建后其值就不能改變,所以 const 對(duì)象必須初始化。該句應(yīng)修改為 const int buf = 10。

(b)和(c)是合法的。

(d)是非法的,sz 是一個(gè) const 對(duì)象,其值不能被改變,當(dāng)然不能執(zhí)行自增操作。

2.27

(a)是非法的,非常量引用 r 不能引用字面值常量 0。修改方法:

int i = -1, &r = i; // 或 const int i = -1, &r = 0; // 或 const int i = -1, &r = i;

(b)是合法的,p2 是一個(gè)常量指針,p2 的值永不改變,即 p2 永遠(yuǎn)指向變量 i2。

(c)是合法的,i 是一個(gè)常量,r 是一個(gè)常量引用,此時(shí) r 可以綁定到字面值常量 0。

(d)是合法的,p3 是一個(gè)常量指針,p3 的值永不改變,即 p3 永遠(yuǎn)指向變量 i2;同時(shí) p3 指向的是常量,即我們不能通過 p3 改變所指對(duì)象的值。

(e)是合法的,p1 指向一個(gè)常量,即我們不能通過 p1 改變所指對(duì)象的值。

(f)是非法的,引用本身不是對(duì)象,因此不能讓引用恒定不變。

(g)是合法的,i2 是一個(gè)常量,r 是一個(gè)常量引用。

2.28

(a)是非法的,cp 是一個(gè)常量指針,因其值(指針存儲(chǔ)的那個(gè)地址)不能被改變,所以必須被初始化。

(b)是非法的,cp2 是一個(gè)常量指針,因其值不能被改變,所以必須被初始化。

(c)是非法的,ic 是一個(gè)常量,因其值不能被改變,所以必須被初始化。

(d)是非法的,p3 是一個(gè)常量指針,因其值不能被改變,所以必須被初始化;同時(shí) p3 所指向的是常量,即我們不能通過 p3 改變所指對(duì)象的值。

(e)是合法的,但是 p 沒有指向任何實(shí)際的對(duì)象。

2.29

(a)是合法的,常量 ic 的值賦給了非常量 i。

(b)是非法的,普通指針 p1 指向了一個(gè)常量,從語(yǔ)法上說,p1 的值可以隨意改變,顯然是不合理的。因?yàn)?p1 改變了,p1 所指對(duì)象因該也同時(shí)改變了,但是 p1 所指對(duì)象是一個(gè)常量,不能被修改。

(c)是非法的,普通指針 p1 指向了一個(gè)常量,錯(cuò)誤情況與上一條類似。

(d)是非法的,p3 是一個(gè)常量指針,不能被賦值。

(e)是非法的,p2 是一個(gè)常量指針,不能被賦值。

(f)是非法的,ic 是一個(gè)常量,不能被賦值。

2.30

頂層 const 表示任意的對(duì)象是常量,而底層 const 與指針和引用等復(fù)合類型的基本類型部分有關(guān)。

解答:v2 和 p3 是頂層 const,分別表示一個(gè)整型常量和一個(gè)整型常量指針;p2 和 r2 是底層 const,分別表示它們所指(所引用)的對(duì)象是常量。

2.31

本題考查頂層 const 和底層 const 對(duì)于拷貝操作的影響。

解答:

在執(zhí)行拷貝操作時(shí),頂層 const 和底層 const 區(qū)別明顯。其中,頂層 const 不受影響,這是因?yàn)榭截惒僮鞑⒉粫?huì)改變被拷貝對(duì)象的值。底層 const 的限制則不容忽視,拷入和拷出的對(duì)象必須具有相同的底層 const 資格,或者兩個(gè)對(duì)象的數(shù)據(jù)類型必須能夠轉(zhuǎn)換。一般說來,非常量可以轉(zhuǎn)換成常量,反之則不行。

r1 = v2; 是合法的,r1 是一個(gè)非常量引用,v2 是一個(gè)常量(頂層 const),把 v2 的值拷貝給 r1 不會(huì)對(duì) v2 有任何影響。

p1 = p2; 是非法的,p1 是普通指針,指向的對(duì)象可以是任意值,p2 是指向常量的指針(底層 const),令 p1 指向 p2 所指的內(nèi)容,有可能錯(cuò)誤地通過 p1 改變 p2 所指常量的值。

p2 = p1; 是合法的,與上一條語(yǔ)句相反,p2 可以指向一個(gè)非常量,只不過我們不會(huì)通過 p2 更改它所指的值。

p1 = p3; 是非法的,p3 包含底層 const 定義(p3 所指的對(duì)象是常量),不能把 p3 的值賦給普通指針。

p2 = p3; 是合法的,p2 和 p3 包含相同的底層 const,p3 的頂層 const 則可以忽略不計(jì)。

2.32

int null = 0, *p = &null; // 或 int null = 0, *p = nullptr;

2.33

【出題思路】

本題旨在考察 auto 說明符與復(fù)合類型、常量混合使用時(shí)的各種情形。首先,使用引用其實(shí)是使用引用的對(duì)象,所以當(dāng)引用被用作初始值時(shí),真正參與初始化的其實(shí)是引用對(duì)象的值,編譯器以引用對(duì)象的類型作為 auto 的推斷類型。其次,auto 一般會(huì)忽略掉頂層 const,同時(shí)保留底層 const。

【解答】

前 3 條賦值語(yǔ)句是合法的,原因如下:

r 是 i 的別名,而 i 是一個(gè)整數(shù),所以 a 的類型推斷結(jié)果是一個(gè)整數(shù);ci 是一個(gè)整型常量,在類型推斷時(shí)頂層 const 被忽略掉了,所以 b 是一個(gè)整數(shù);cr 是 ci 的別名,而 ci 是一個(gè)整型常量,所以 c 的類型推斷結(jié)果是一個(gè)整數(shù)。因?yàn)?a、b、c 都是整數(shù),所以為其賦值 42 是合法的。

后 3 條賦值語(yǔ)句是非法的,原因如下:

i 是一個(gè)整數(shù),&i 是 i 的地址,所以 d 的類型推斷結(jié)果是一個(gè)整型指針;ci 是一個(gè)整型常量,&ci 是一個(gè)整型常量的地址,所以 e 的類型推斷結(jié)果是一個(gè)指向整型常量的指針;ci 是一個(gè)整型常量,所以 g 的類型推斷結(jié)果是一個(gè)整型常量引用。因?yàn)?d 和 e 都是指針,所以不能直接用字面值常量為其賦值;g 綁定到了整型常量,所以不能修改它的值。

2.34

【出題思路】

本題旨在考察 auto 說明符與復(fù)合類型、常量混合使用時(shí)的各種情形。

【解答】

基于上一個(gè)練習(xí)中的變量和語(yǔ)句編寫的程序如下所示:

#include <iostream>using namespace std; int main(int argc, char *argv[]) {int i = 0, &r = i;auto a = r;const int ci = i, &cr = ci;auto b = ci;auto c = cr;auto d = &i;auto e = &ci;const auto f = ci;auto &g = ci;cout << a << " " << b << " " << c << " " << d << " " << e << " " << g << std::endl;a = 42;b = 42;c = 42;// d = 42;// e = 42;// g = 42;cout << a << " " << b << " " << c << " " << d << " " << e << " " << g << std::endl;return 0; } // 運(yùn)行結(jié)果 0 0 0 0x7ffee3e7088c 0x7ffee3e70878 0 42 42 42 0x7ffee3e7088c 0x7ffee3e70878 0Process finished with exit code 0

2.35

【出題思路】

本題旨在考察 auto 說明符與復(fù)合類型、常量混合使用時(shí)的各種情形。

【解答】

由題意可知,i 是一個(gè)整型常量,j 的類型推斷結(jié)果是整數(shù),k 的類型推斷結(jié)果是整型常量,p 的類型推斷結(jié)果指向整型常量的指針,j2 的類型推斷結(jié)果是整型常量,k2 的類型推斷結(jié)果是整型常量的引用。

  • i is const int
  • j is int
  • k is const int &
  • p is const int *
  • j2 is const int
  • k2 is const int &

用于驗(yàn)證的程序是:

#include <iostream> #include <typeinfo>int main() {const int i = 42;auto j = i;const auto &k = i;auto *p = &i;const auto j2 = i, &k2 = i;std::cout << typeid(i).name() << std::endl; // istd::cout << typeid(j).name() << std::endl; // istd::cout << typeid(k).name() << std::endl; // istd::cout << typeid(p).name() << std::endl; // PKistd::cout << typeid(j2).name() << std::endl; // istd::cout << typeid(k2).name() << std::endl; // istd::cout << std::endl;std::cout << std::boolalpha; // 接下來的輸出把 bool 值顯示成 true/falsestd::cout << "i and j have same type? "<< std::is_same<decltype(i), decltype(j)>::value << std::endl;std::cout << "i and k have same type? "<< std::is_same<decltype(i), decltype(k)>::value << std::endl;std::cout << "i and j2 have same type? "<< std::is_same<decltype(i), decltype(j2)>::value << std::endl;std::cout << "j and j2 have same type? "<< std::is_same<decltype(j), decltype(j2)>::value << std::endl;std::cout << "k and k2 have same type? "<< std::is_same<decltype(k), decltype(k2)>::value << std::endl;return 0; } // 運(yùn)行結(jié)果 // print i means int, and PKi means pointer to const int. i i i PKi i ii and j have same type? false i and k have same type? false i and j2 have same type? true j and j2 have same type? false k and k2 have same type? trueProcess finished with exit code 0

2.36

【出題思路】

本題旨在考察 decltype 與引用的關(guān)系。對(duì)于 decltype 所用的表達(dá)式來說,如果變量名加上一對(duì)括號(hào),得到的類型與不加括號(hào)時(shí)會(huì)有不同。具體來說,如果 decltype 使用的是一個(gè)不加括號(hào)的變量,則得到的結(jié)果就是該變量的類型;如果給變量加上了一層或多層括號(hào),編譯器就會(huì)把它當(dāng)成一個(gè)表達(dá)式,從而推斷得到引用類型。

【解答】

在本題的程序中,初始情況下 a 的值是 3,b 的值是4。decltype(a) c = a; 使用的是一個(gè)不加括號(hào)的變量,因此 c 的類型就是 a 的類型,即該語(yǔ)句等同于 int c = a;,此時(shí) c 是一個(gè)新整型變量,值為 3。decltype((b)) d = a; 使用的是一個(gè)加了括號(hào)的變量,因此 d 的類型是引用,即該語(yǔ)句等同于 int &d = a;,此時(shí) d 是變量 a 的別名。

執(zhí)行 ++c; ++d; 時(shí),變量 c 的值自增為 4,因?yàn)?d 是 a 的別名,所以 d 自增 1 意味著 a 的值變成了 4。當(dāng)程序結(jié)束時(shí),a、b、c、d 的值都是 4。

#include <iostream> #include <typeinfo>int main() {int a = 3, b = 4;decltype(a) c = a;decltype((b)) d = a;++c;++d;std::cout << typeid(c).name() << std::endl; // intstd::cout << typeid(d).name() << std::endl; // int &std::cout << c << std::endl; // 4std::cout << d << std::endl; // 4return 0; }

2.37

【出題思路】

decltype 的參數(shù)既可以是普通變量,也可以是一個(gè)表達(dá)式。當(dāng)參數(shù)是普通變量時(shí),推斷出的類型就是該變量的類型;當(dāng)參數(shù)是表達(dá)式時(shí),推斷出的類型是引用。

【解答】

根據(jù) decltype 的上述性質(zhì)可知,c 的類型是 int,值為 3;表達(dá)式 a = b 作為decltype 的參數(shù),編譯器分析表達(dá)式并得到它的類型作為 d 的推斷類型,但是不實(shí)際計(jì)算該表達(dá)式,所以 a 的值不發(fā)生改變,仍然是 3;d 的類型是 int &,d 是 a 的別名,值是 3;b 的值一直沒有發(fā)生改變,為 4。

2.38

【出題思路】

auto 和 decltype 是兩種類型推斷的方式,本題旨在考察二者的區(qū)別和聯(lián)系。

【解答】

auto 和 decltype 的區(qū)別主要有三方面:

  • auto 類型說明符用編譯器計(jì)算變量的初始值來推斷其類型,而 decltype 雖然也讓編譯器分析表達(dá)式并得到它的類型,但是不實(shí)際計(jì)算表達(dá)式的值。
  • 編譯器推斷出來的 auto 類型有時(shí)候和初始值的類型并不完全一樣,編譯器會(huì)適當(dāng)?shù)馗淖兘Y(jié)果類型使其更符合初始化規(guī)則。例如,auto 一般會(huì)忽略掉頂層 const,而把底層 const 保留下來。與之相反,decltype 會(huì)保留變量的頂層 const。
  • 與 auto 不同,decltype 的結(jié)果類型與表達(dá)式密切相關(guān),如果變量名加上了一對(duì)括號(hào),則得到的類型與不加括號(hào)時(shí)會(huì)有不同。如果 decltype 使用的是一個(gè)不加括號(hào)的變量,則得到的結(jié)果就是該變量的類型;如果給變量加上了一層或多層括號(hào),則編譯器將推斷得到引用類型。
  • 一個(gè)用以說明的示例如下所示:

    #include <iostream> #include <typeinfo>int main() {int a = 3;auto c1 = a;decltype(a) c2 = a;decltype((a)) c3 = a;const int d = 5;auto f1 = d;decltype(d) f2 = d;std::cout << typeid(c1).name() << std::endl; // intstd::cout << typeid(c2).name() << std::endl; // intstd::cout << typeid(c3).name() << std::endl; // int &std::cout << typeid(f1).name() << std::endl; // intstd::cout << typeid(f2).name() << std::endl; // const intc1++;c2++;c3++;f1++;// f2++; // 錯(cuò)誤:f2 是整型常量,不能執(zhí)行自增操作std::cout << a << " " << c1 << " " << c2 << " " << c3 << " " << f1<< " " << f2 << std::endl;return 0; } // 運(yùn)行結(jié)果 i i i i i 4 4 4 4 6 5Process finished with exit code 0

    對(duì)于第一組類型推斷來說,a 是一個(gè)非常量整數(shù),c1 的推斷結(jié)果是整數(shù),c2 的推斷結(jié)果也是整數(shù),c3 的推斷結(jié)果由于變量 a 額外加了一對(duì)括號(hào)所以是整數(shù)引用。c1、c2、c3 依次執(zhí)行自增操作,因?yàn)?c3 是變量的 a 的別名,所以 c3 自增等同于 a 自增,最終 a、c1、c2、c3 的值都變?yōu)?4。

    對(duì)于第二組類型推斷來說,d 是一個(gè)常量整數(shù),含有頂層 const,使用 auto 推斷類型自動(dòng)忽略掉頂層 const,因此 f1 的推斷結(jié)果是整數(shù);decltype 則保留頂層 const,所以 f2 的推斷結(jié)果是整數(shù)常量。f1 可以正常執(zhí)行自增操作,而常量 f2 的值不能被改變,所以無法自增。

    附:

    • What is the difference between auto and decltype(auto) when returning from a function?
    • decltype vs auto

    2.39

    #include <iostream>struct Foo { /* 此處為空 */} // 注意:沒有分號(hào) int main() {return 0; } // 編譯無法通過 main.cpp:3:33: error: expected ';' after struct

    【出題思路】

    本題旨在考查類定義的語(yǔ)法規(guī)范,尤其要注意類體結(jié)束之后的分號(hào)必不可少。

    【解答】

    該程序無法編譯通過,原因是缺少了一個(gè)分號(hào)。因?yàn)轭愺w后面可以緊跟變量名以示對(duì)該類型對(duì)象的定義,所以在類體右側(cè)表示結(jié)束的花括號(hào)之后必須寫一個(gè)分號(hào)。

    稍作修改,程序就可以編譯通過了。

    #include <iostream>struct Foo { /* 此處為空 */}; int main() {return 0; } Process finished with exit code 0

    2.40

    【出題思路】

    類的設(shè)計(jì)源于實(shí)際應(yīng)用,設(shè)計(jì) Sales_data 類的關(guān)鍵是理解在銷售過程中應(yīng)該包含哪些數(shù)據(jù)元素,同時(shí)為每個(gè)元素設(shè)定合理的數(shù)據(jù)類型。

    【解答】

    原書中的程序包含 3 個(gè)數(shù)據(jù)成員,分別是 bookNo(書籍編號(hào))、units_sold(銷售量)、revenue(銷售收入),新設(shè)計(jì)的 Sales_data 類細(xì)化了銷售收入的計(jì)算方式,在保留 bookNo 和 units_sold 的基礎(chǔ)上,新增了 sellingprice(零售價(jià)、原價(jià))、saleprice(實(shí)售價(jià)、折扣價(jià))、discount(折扣),其中 discount = saleprice / sellingprice。

    #include <iostream>struct Sales_data {std::string bookNo; // 書籍編號(hào)unsigned units_sold = 0; // 銷售量double sellingprice = 0.0; // 零售價(jià)double saleprice = 0.0; // 實(shí)售價(jià)double discount = 0.0; // 折扣 }; int main() {return 0; }

    2.41

    Sales_data.h

    #ifndef SALESDATA_H // we're here only if SALESDATA_H has not yet been defined #define SALESDATA_H// Definition of Sales_data class and related functions goes here #include <iostream> #include <string>// 頭文件不應(yīng)包含 using 聲明 // using namespace std;class Sales_data {// 友元函數(shù)friend std::istream &operator>>(std::istream &, Sales_data &);// 友元函數(shù)friend std::ostream &operator<<(std::ostream &, const Sales_data &);// 友元函數(shù)friend bool operator<(const Sales_data &, const Sales_data &);// 友元函數(shù)friend bool operator==(const Sales_data &, const Sales_data &);public: // 構(gòu)造函數(shù)的 3 種形式Sales_data() = default;Sales_data(const std::string &book) : bookNo(book) {}Sales_data(std::istream &is) { is >> *this; }Sales_data &operator+=(const Sales_data &);std::string isbn() const { return bookNo; }private:std::string bookNo; // 書籍編號(hào),隱式初始化為空串unsigned units_sold = 0; // 銷售量,顯式初始化為 0double sellingprice = 0.0; // 原始價(jià)格,顯式初始化為 0.0double saleprice = 0.0; // 實(shí)售價(jià)格,顯式初始化為 0.0double discount = 0.0; // 折扣,顯式初始化為 0.0 };inline bool compareIsbn(const Sales_data &lhs, const Sales_data &rhs) {return lhs.isbn() == rhs.isbn(); }Sales_data operator+(const Sales_data &, const Sales_data &);inline bool operator==(const Sales_data &lhs, const Sales_data &rhs) {return lhs.units_sold == rhs.units_sold &&lhs.sellingprice == rhs.sellingprice &&lhs.saleprice == rhs.saleprice &&lhs.isbn() == rhs.isbn(); }inline bool operator!=(const Sales_data &lhs, const Sales_data &rhs) {return !(lhs == rhs); // 基于運(yùn)算符 == 給出 != 的定義 }Sales_data &Sales_data::operator+=(const Sales_data &rhs) {units_sold += rhs.units_sold;saleprice = (rhs.saleprice * rhs.units_sold + saleprice * units_sold)/ (rhs.units_sold + units_sold);if (sellingprice != 0)discount = saleprice / sellingprice;return *this; }Sales_data operator+(const Sales_data &lhs, const Sales_data &rhs) {Sales_data ret(lhs); // 把 lhs 的內(nèi)容拷貝到臨時(shí)變量 ret 中,這種做法便于運(yùn)算ret += rhs; // 把 rhs 的內(nèi)容加入其中return ret; // 返回 ret }std::istream &operator>>(std::istream &in, Sales_data &s) {in >> s.bookNo >> s.units_sold >> s.sellingprice >> s.saleprice;if (in && s.sellingprice != 0)s.discount = s.saleprice / s.sellingprice;elses = Sales_data(); // 輸入錯(cuò)誤,重置輸入的數(shù)據(jù)return in; }std::ostream &operator<<(std::ostream &out, const Sales_data &s) {out << s.isbn() << " " << s.units_sold << " "<< s.sellingprice << " " << s.saleprice << " " << s.discount;return out; }#endif

    重寫練習(xí) 1.20

    main.cpp

    #include <iostream> #include "Sales_data.h"using namespace std;int main() {Sales_data book;std::cout << "請(qǐng)輸入銷售記錄:" << std::endl;// 輸入格式:ISBN 售出本數(shù) 原始價(jià)格 實(shí)際售價(jià)while (std::cin >> book) {std::cout << "ISBN、售出本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為:" << book << std::endl;}return 0; } // 運(yùn)行結(jié)果 請(qǐng)輸入銷售記錄: 0-201-78345-X 3 20.00 19.00 ISBN、售出本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為:0-201-78345-X 3 20 19 0.95 0-202-78345-X 4 30.00 29.00 ISBN、售出本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為:0-202-78345-X 4 30 29 0.966667

    重寫練習(xí) 1.21

    main.cpp

    #include <iostream> #include "Sales_data.h"using namespace std;int main() {Sales_data trans1, trans2;std::cout << "請(qǐng)輸入兩條 ISBN 相同的銷售記錄:" << std::endl;std::cin >> trans1 >> trans2;if (compareIsbn(trans1, trans2))std::cout << "匯總信息:ISBN、銷售本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為:"<< "\n" << trans1 + trans2 << std::endl;elsestd::cout << "兩條銷售記錄的 ISBN 不同" << std::endl;return 0; } // 運(yùn)行結(jié)果 請(qǐng)輸入兩條 ISBN 相同的銷售記錄: 0-201-78345-X 3 20.00 19.00 0-201-78345-X 5 20.00 18.00 匯總信息:ISBN、銷售本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為: 0-201-78345-X 8 20 18.6154 0.930769Process finished with exit code 0

    重寫練習(xí) 1.22

    main.cpp

    #include <iostream> #include "Sales_data.h"using namespace std;int main() {Sales_data total, trans;std::cout << "請(qǐng)輸入幾條 ISBN 相同的銷售記錄:" << std::endl;// 每次輸入要求 ISBN 相同,售出本數(shù)隨便,原始價(jià)格相同,實(shí)售價(jià)格隨便if (std::cin >> total) {while (std::cin >> trans)if (compareIsbn(total, trans))total += trans;else { // ISBN 不同std::cout << "當(dāng)前書籍 ISBN 不同" << std::endl;break;}std::cout << "有效匯總信息:ISBN、售出本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為:"<< "\n" << total << std::endl;} else {std::cout << "沒有數(shù)據(jù)" << std::endl;return -1;}return 0; } // 運(yùn)行結(jié)果(實(shí)售價(jià)格為均值,具體可查看 Sales_item.h 運(yùn)算符 += 重載的實(shí)現(xiàn) 請(qǐng)輸入幾條 ISBN 相同的銷售記錄: 0-201-78345-X 3 20.00 19.00 0-201-78345-X 5 20.00 29.00 0-202-78345-Y 2 200.00 199.00 當(dāng)前書籍 ISBN 不同 有效匯總信息:ISBN、售出本數(shù)、原始價(jià)格、實(shí)售價(jià)格、折扣為: 0-201-78345-X 8 20 22.8462 1.14231Process finished with exit code 0

    重寫練習(xí) 1.23

    #include <iostream> #include "Sales_data.h"using namespace std;int main() {Sales_data trans1, trans2;int num = 1; // 記錄當(dāng)前書籍的銷售記錄總數(shù)std::cout << "請(qǐng)輸入若干銷售記錄:" << std::endl;if (std::cin >> trans1) {while (std::cin >> trans2) {if (compareIsbn(trans1, trans2)) // ISBN 相同num++;else { // ISBN 不同std::cout << trans1.isbn() << " 共有 "<< num << " 條銷售記錄" << std::endl;trans1 = trans2;num = 1;}std::cout << trans1.isbn() << " 共有 "<< num << " 條銷售記錄" << std::endl;}} else {std::cout << "沒有數(shù)據(jù)" << std::endl;return -1;}return 0; } // 運(yùn)行結(jié)果 請(qǐng)輸入若干銷售記錄: 0-201-78345-X 3 20.00 19.00 0-201-78345-X 2 20.00 18.00 0-201-78345-X 共有 2 條銷售記錄 0-201-78345-X 5 20.00 19.00 0-201-78345-X 共有 3 條銷售記錄 0-202-78345-Y 3 220.00 129.00 0-201-78345-X 共有 3 條銷售記錄 0-202-78345-Y 共有 1 條銷售記錄 0-201-78345-X 7 20.00 19.99 0-202-78345-Y 共有 1 條銷售記錄 0-201-78345-X 共有 1 條銷售記錄

    注:1.6 節(jié)練習(xí)與重寫練習(xí) 1.23 相同

    2.42

    2.41 已實(shí)現(xiàn)該題功能

    轉(zhuǎn)載于:https://www.cnblogs.com/kafffka/p/10963854.html

    《新程序員》:云原生和全面數(shù)字化實(shí)踐50位技術(shù)專家共同創(chuàng)作,文字、視頻、音頻交互閱讀

    總結(jié)

    以上是生活随笔為你收集整理的第 2 章的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。

    主站蜘蛛池模板: av毛片观看 | 你懂的国产视频 | 超碰caopor | www.av麻豆| 日本东京热一区二区 | 亚洲网站在线免费观看 | 国产成人主播 | 激情综合网av | 波多野结衣丝袜 | 岛国av一区二区三区 | www.看毛片| 久久国产区 | 亚洲精品男女 | 日韩欧美视频在线播放 | 秋霞网一区二区三区 | 精品xxxxx | 亚洲人成色777777老人头 | 亚洲久久久 | 日本成人午夜视频 | 最新毛片网| 一二三四av | 国产一级免费片 | 欧美激情一二区 | 亚洲成人中文 | jizzzxxxx | 美女三级视频 | youjizz在线视频 | 强行侵犯视频在线观看 | 91在线亚洲 | 欧美三级国产 | 亚洲天堂999 | 国产自产| 久久av网址 | 久久久精品久久久 | 欧美精品1区2区3区 精品成人一区 | 日日人人| 国产精品815.cc红桃 | 亚洲69视频 | jizz欧美大全 | 欧美黄色大片免费观看 | 青青青视频免费 | 黄色a级片在线观看 | 亚洲AV成人无码久久精品同性 | 激情黄色小视频 | 国产精品麻豆果冻传媒在线播放 | 一级成人免费视频 | av福利片 | 国产精品自拍网站 | 在线免费看黄网站 | 久久国产黄色片 | 国产精品影院在线观看 | 男女超爽视频免费播放 | 亚洲女人的天堂 | 日本福利一区二区三区 | 歪歪视频在线观看 | 性做久久久久 | 人妻熟女一区二区三区app下载 | 手机看片中文字幕 | 狠狠欧美 | 伊人网视频在线 | 加勒比毛片| 福利电影一区二区 | 欧美久操 | www日韩在线观看 | 成av人在线观看 | av国产片 | 国产高清在线观看视频 | 日韩在线播放视频 | 人人干人| 精品69| 国产ts系列 | 欧洲视频一区二区三区 | 亚洲一区二区在线视频 | 国产一区二区观看 | 国产精品视频你懂的 | 伊人久久亚洲综合 | 欧洲精品久久久久毛片完整版 | 欧洲一区二区 | 一级的大片 | 永久免费在线看片 | 国产美女无遮挡免费 | 亚洲情热 | 免费av网站在线观看 | 国产日韩欧美一区 | 18成人免费观看网站下载 | 精品一区二区三区毛片 | 久久中字 | 男女调教视频 | 国产白丝袜美女久久久久 | 与亲女洗澡时伦了毛片 | 亚洲国产电影在线观看 | 日日噜噜夜夜爽爽 | 日本一区二区观看 | 曰批女人视频在线观看 | 亚洲欧美日韩在线一区二区 | 国产一区二区三区免费观看视频 | 久久亚洲私人国产精品va | 精品少妇一区二区三区密爱 | 丰满人妻一区二区 |