標籤:
1. 輸入輸出的本質
C++中的輸入輸出都是通過流來進行的,而具體的輸出輸入都是通過對流進行操作來完成的,一般為定向一個流(重新導向),清空流,向流裡邊添加新的元素。C++把輸入輸出看做位元組流,輸入時從位元組流中抽取位元組,輸出時把位元組插入到位元組流中。
2.使用cin及其方法進行輸入
cin對象將標準輸入表示為位元組流,通常情況下用鍵盤來產生這種位元組流,常用的cin輸入發方法為cin>>abc;而istream類對抽取運算子進行了重載,是之可以識別這些基本類型,unsigned/signed char&, char&, short&, unsigned short&, int&,unsigned int&,long&, unsigned long&, long long &, unsigned long long &, float& double &, long double&;對於這些基本類型直接就用cin加抽取運算子>>就可以實現。有個問題就在於>>抽取符會跳過分行符號且回忽略類似於空白,製表之類的字元,所以這樣的一段程式是有問題的,這段代碼裡面的迴圈將會永遠的跑下去,單純地用這種方法進行對字元類資料的輸入就出現了很大的問題。
而對於要輸入一個字串如果用cin>>input;這樣的方法來輸入一個字串,則遇到空白換行,製表之類的,輸入都會停止
1 char a; 2 int times=0; 3 cin>>a; 4 while(a!=‘\n‘) 5 { 6 cout<<a; 7 cin>>a; 8 times++; 9 }10 cout<<times;
3. c++對字串,字元,string類的輸入//一下方法很好的解決了空白,換行等不被讀取的情況。
C++對字串,字元和string類輸入的時候常用的get(),getline()函數,他們被稱為非格式化輸入,因為他們唯讀取字元,包括空白 ,分行符號, 定位字元,等也不會進行資料轉換,讀到啥就是啥。
在istream裡邊定義的get()函數與getline()函數:
用get進行單字元輸入,在有參數或者沒有參數的情況下,get函數讀取一個輸入字元,不管這個字元是啥換行,製表都可以,直接讀進去。
其中get(void)將字元轉換成整形後返回,對於get(char&)函數返回一個指向的調用它的istream對象的引用,這樣就可以使用類似於cin.get(a).get(b).get(c);的方式來讀取,這其中要注意get不會忽略分行符號,所以要注意分行符號被不小心讀進去的情況。
如果讀取倒了檔案尾,或者鍵盤輸入的尾部等沒東西可讀的情況的時候,cin.get(ch);會返回false,其餘正常情況返回的都是true。
cin.get()與cin.get(ch)的比較
| 特徵 |
cin.get(ch) |
ch=cin.get() |
| 傳輸輸入特徵 |
直接賦值給ch |
把函數傳回值賦給ch |
| 讀取到字元之後函數返回至 |
指向istream對象的引用 |
字元編碼,其實是int值 |
| 達到檔案尾時函數的傳回值 |
轉換為false |
EOF |
註:鍵盤輸入模擬的檔案尾與真正的檔案尾效果一樣
get()函數
在istream中定義的get()函數一共有六項重載:使用的時候只要符合任意一種參數規則即可
1. int_type __CLR_OR_THIS_CALL get();//無參數,唯讀取一個字元,傳回值為int型
2. _Myt& __CLR_OR_THIS_CALL get(_Elem *_Str, streamsize _Count);//接受兩個參數,一個字串首地址,一個int型的形參來控制最大讀取字元數,為存放字串末尾 //的/0,這個參數要比讀取的字串大一,該函數預設分界符為/n.
3. _Myt& __CLR_OR_THIS_CALL get(_Elem *_Str, streamsize _Count, _Elem _Delim);//與上邊基本相同,不同之處在於這個函數分界符為自己定的_Delim.
4._Myt& __CLR_OR_THIS_CALL get(_Elem& _Ch);//接收參數為char型的引用,起作用就是把值直接賦給ch;
//在測試函數的時候有點發現,不能對字串進行引用,因為數組是一個由若干個元素所組成的集合,所以無法建立一個數組的別名。
如果這塊是 char &bbb = input[10]; //不能建立數組的引用。
//這塊效果就是對input[0]進行引用。
5._Myt& __CLR_OR_THIS_CALL get(_Mysb& _Strbuf);
6._Myt& __CLR_OR_THIS_CALL get(_Mysb& _Strbuf, _Elem _Delim);//除第一個函數外其他函數傳回值均為指向調用它的istream對象的引用。
以上函數在使用的時候都要主意只能使用cin.get(若干參數或者沒有),get()函數在遇到分行符號讀取完字元時並不會讀取分行符號或者是本來的預設分界符,而這些東西都只會留在原始流之內,
char input[10]char ch;cin.get(input,10,‘a‘);cout << input << endl;cin.get(ch);cout<<ch<<endl;
輸入sdsdsda
輸出sdsdsd
a
getline()函數
在istream之中的getline()函數一共兩項重載
1. _Myt& __CLR_OR_THIS_CALL getline(_Elem *_Str, streamsize _Count);
2. _Myt& __CLR_OR_THIS_CALL getline(_Elem *_Str, streamsize _Count, _Elem _Delim);
這兩個函數類似於get()函數中的2 、3重載,其不同之處在於getline()函數會自動丟棄分行符號等分界符。
char input[10]char ch;cin.getline(input,10,‘a‘);cout << input << endl;cin.get(ch);cout<<ch<<endl;
輸入 sdsdsda
輸出sdsdsd
因為丟棄分界符,則分界符a被丟棄,下面的cin.get(ch)讀到的是分行符號,所以輸出的時候就只是輸出一個分行符號。
對string類的輸入
單純的應cin>>來輸入一個string類字串,則會在遇到空白,製表,換行等停止。
用getline()來讀取string類, getline()在vs2010中函數定義在string檔案中,共兩個重構,且都為內嵌函式
1. template<class _Elem,
class _Traits,
class _Alloc> inline
basic_istream<_Elem, _Traits>& getline(
basic_istream<_Elem, _Traits>& _Istr,
basic_string<_Elem, _Traits, _Alloc>& _Str,
const _Elem _Delim)//使用的是自己定義的分界符,其參數為流定向類,第二個參數為輸出目標string,第三個參數為自訂分界符
2. template<class _Elem,
class _Traits,
class _Alloc> inline
basic_istream<_Elem, _Traits>& getline(
basic_istream<_Elem, _Traits>& _Istr,
basic_string<_Elem, _Traits, _Alloc>& _Str)//預設的分界符為\n
這兩個函數都沒有字串字元數上限的參數,因為string類會自己自動根據字串的大小來調整大小。
C++輸入輸出總結_輸入