C++ Primer Plus 筆記第五章
for循環的組成部分:
1. 設置初始值。
2. 執行測試,看看循環是否應當繼續進行。
3. 執行循環操作。
4. 更新用於測試的值。
表達式和語句:
表達式:任何值和任何有效的值和操作符的組合都是表達式。每個C++表達式都有值。
語句:所有表達式加上分號,都可以成為語句。有的沒有意義。
副作用和順序點:
副作用:指在計算表達式時對某些東西(存儲在變量中的值)進行了修改。
順序點:程序執行過程中的一個點,進入下一步之前將確保對所有副作用都進行了評估。
前綴和後綴格式:
1 for (n = lim; n > 0; --n)
. . .;
2 for (n = lim; n > 0; n--)
. . .;
因為表達式(--n和n--)中的值均為被使用,只存在副作用。兩條語句最終效果相同。
執行效率上有略微的差別,前綴版本效率較高。
遞增/遞減操作符和指針:
前綴遞增、前綴遞減和解除引用操作符的優先級相同,以從右向左的方式進行結合;
後綴遞增和後綴遞減的優先級高於前綴操作符 ,從左到右的方式結合;
double arr[5] = {21.1, 32.8, 23.4, 45.2, 37.4}; double *pt = arr; // pt指向arr[0],to 21.1 ++pt; // pt指向arr[1],to 32.8 *++pt; // *(++pt) 23.4 ++*pt; // ++(*pt) 24.4 (*pt)++; // 25.4 pt仍指向arr[2] *pt++; // 後綴操作符‘++‘的優先級更高,所以‘++‘的操作符用於pt,*pt++的值為25.4,pt指向arr[3]的地址
組合賦值操作符:
eg: += /= -= *= :
將結果賦給左側操作數
關系表達式:
C++提供6種關系操作符來對數字、字符(ASCII碼)和string類對象進行比較(不能用於C-風格字符串):
操作符 < <= == > >= !=
含義 小於 小於或等於 等於 大於 大於或等於 不等於
C-風格字符串比較:
strcmp() 函數接收兩個字符串地址作為參數,參數可以是指針、字符串常量或者字符數組名。
strcmp(a,b) 頭文件cstring:
如果兩個字符串相同,該函數返回零;
如果a > b,返回一個正數;
如果a < b,返回負數
char字符變量可以使用遞增操作符和遞減操作符,因為char類型實際上是整型。(ch++,ch--)
比較string類字符串:
sting類字符串,類的設計能使用關系操作符進行比較;
While循環:
while循環沒有初始化和更新部分的for循環,只有測試條件和循環條件:
while ( test_condition )
body
與for循環一樣,while循環也是一種入口條件循環
for與while:
for與while本質相同;
使用for循環來為循環計數,for循環允許將所有相關信息—初始值、終止值和更新計數器放在一個地方;
在無法預知循環將執行的次數時,程序員常使用while循環
等待一段時間:編寫延時循環
clock():返回程序開始執行後所用的系統時間,
問題一:clock() 返回的時間不一定是秒;
問題二:函數的返回類型下某些系統上可能是long,unsigned long或其他類型
頭文件ctime提供了這些問題的解決方法:
解決問題一:定義符號常量:CLOCK_PER_SEC 每秒鐘包含的系統時間單位數
解決問題二:將clock_t作為clock() 返回類型別名,把變量聲明為clock_t
waiting.cpp
1 #include <iostream> 2 #include <ctime> 3 using namespace std; 4 5 int main() 6 { 7 cout << "Enter the delay time, in seconds: "; 8 float secs; 9 cin >> secs; 10 clock_t delay = secs * CLOCKS_PER_SEC; 11 cout << "staring\a\n"; 12 clock_t start = clock(); 13 while(clock() - start < delay) 14 . 15 . 16 . 17 cout << "done \a\n"; 18 return 0; 19 }
改程序以系統時間為單位(而不是秒)計算延遲時間,避免了在每輪循環中將系統時間轉換為秒
類型別名:
C++為類型創建別名的方式有兩種:
使用預處理器: #define BYTE char // 將BYTE聲明為char類型別名
使用typedef: typedef char byte;
通用格式:typedef typeName aliasName; // 將aliasName聲明為typeName類型的別名
typedef char* byte_pointer; // 將byte_pointer聲明為 char指針別名
typedef是一種更加的選擇——有時候也是唯一的選擇
註意:typedef 不會創建新類型,只是為已有的類型創建別名
do while循環:
do while 是出口條件循環,先執行循環體,再判定測試表達式,決定是否繼續執行循環;
eg:
do
{
cin >> n;
} while( n != 7);
程序必須先進入循環體獲得輸入。
循環和文本讀取:
使用原始的cin進行輸入:
程序清單 testin1.cpp
1 #include<iostream> 2 using namespace std; 3 4 int main() 5 { 6 char ch; 7 int count = 0; 8 cout << "Enter characters; enter # to quit: \n"; 9 cin >> ch; 10 while( ch != ‘#‘) 11 { 12 cout << ch; 13 ++count; 14 cin >> ch; 15 } 16 cout << endl << count << "characters read\n"; 17 return 0; 18 }
cin在讀取char值時(cin >> ch),與讀取其他基本類型一樣,忽略空格和換行符;
操作系統回顯輸入:see ken run#really fast <Enter>;
測試程序回顯輸入:seekenrun;
發送給cin的輸入被緩沖,回車後,輸入內容被發送給程序
使用cin.get(char)進行補救:
字符讀取程序要檢查每個字符,包括空格、制表符和換行符。cin所屬的iostream類中包含成員函數cin.get (ch) 讀取輸入中的下一個字符賦給變量ch;
替換 textin1.cpp 中 cin >> ch :
1 #include<iostream> 2 using namespace std; 3 4 int main() 5 { 6 char ch; 7 int count = 0; 8 cout << "Enter characters; enter # to quit: \n"; 9 cin.get(ch); 10 while( ch != ‘#‘) 11 { 12 cout << ch; 13 ++count; 14 cin.get(ch); 15 } 16 cout << endl << count << "characters read\n"; 17 return 0; 18 }
頭文件 iostream 將 cin.get (ch) 函數原型的參數聲明為引用類型,因此該函數可以修改其參數的值
cin.get 函數重載:
C++支持被稱為函數重載的OOP特性——允許創建多個同名函數,參數列表不同
cin.get ( name, ArSize ):編譯器使用接受參數 char* 和 int 版本;
cin.get (ch):編譯器使用接收一個參數 char 版本 ,返回一個cin對象; cin.get(ch1) .get(ch2);
cin.get():不接收任何參數的成員函數返回輸入中的下一個字符,ch = cin.get (),將字符編碼作為 int 值返回
文件尾條件EOF:
while ( cin.fail () == false ) // 檢測EOF
常見的字符輸入做法:
cin.get (ch);
while ( cin.fail() == false) or while ( !cin.fail() ) or while ( cin.get( ch) )
{
. . .
cin.get ( ch );
}
cin.get( char ) 返回值是一個cin對象,iostream類提供一個將istream對象轉換為bool值的函數
C++ Primer Plus 筆記第五章