使用char類型的變量我們可以表示單個字符,那麼,我們又該如何表示擁有多個字符的字符串呢? 我們注意到,一個字符串是由多個字符串連起來形成的。很自然地,一種最簡單直接的方法就是利用數組(一種數據組織管理方式,它將多個相同類型的數據元素組織起來,形成一個數據序列以便於訪問。更多可以參考後文3.6小節對數組的介紹)來保存一個字符串中的各個字符,最後用一個特殊字符‘\0’表示字符串的結束,以此來將多個char類型的字符數據串聯成字符串。例如:
// 定義一個字符數組,用以保存字符串 char msg[32]; // 將各個字符依次保存到數組相應位置上 msg[0] = 'G'; // 第一個字符,保存到數組的第一個位置,後面的以此類推 msg[1] = 'o'; msg[2] = 'o'; msg[3] = 'd'; // 在最後的位置保存一個‘\0’,表示字符串結束 msg[4] = '\0'; // 輸出msg數組中的字符串 cout<<msg<<endl;
用字符數組表示字符串的方式雖然簡單可行,可是卻有諸多使用上的不便。在C++中,我們更多地是用STL(Standard Template Library,標准模板庫,是利用模板技術實現的一套函數庫,其中提供了一些常用的容器和算法以便於對數據進行處理。這裡的字符串類型 string就是由它定義的一種用以表示字符串的數據類型。關於STL,在稍後的第8章中我們還將詳細介紹)中定義好的字符串類型string來表示字符串。這種字符串類型實質上是對一個char類型字符數組的包裝,在保存字符串數據的同時還增加了一些對字符串的常用操作,比如獲取字符串長度,查找特定字符等,這樣字符串的處理就方便多了。就像char和wchar_t相互對應處理不同范圍的字符一樣,與string對應的,C++還提供了可以處理wchar_t類型字符的wstring字符串類型。例如:
#include <iostream> #include <string> // string類型所在的頭文件 using namespace std; int main() { // 定義一個string類型變量,表示英文字符串 string strEn = "Good Morning!"; // 定義一個wstring類型變量,表示中文字符串 wstring strChs = L"陝A-82103"; // 用cout輸出string類型字符串 // 用wcout輸出wstring類型字符串 cout<<strEn; wcout.imbue( locale ( "chs" ) ); // 設置區域 wcout<<strChs<<endl; return 0; }
可以看到,因為string和wstring編碼方式的不同,不同的字符串在輸出的時候需要采用不同的方式。對於wstring類型的字符串變量,在輸出的時候需要使用wcout對象,並且需要用imbue()函數設定字符的編碼方式。另外,這裡值得指出的一點是,英文字符串不僅可以用string類型表示,也可以使用wstring類型表示,而中文字符串則只能使用wstring類型表示。
string類型不僅包裝了字符數組,可以存儲字符串中的各個字符,同時還提供了很多跟字符串相關的操作,例如,可以獲得一個字符串的長度,或者在字符串中查找某個字符等等,極大地方便了對字符串的處理。例如:
// 定義一個字符串變量,用於保存用戶輸入的用戶名 string strName = ""; cout<<"請輸入用戶名:"<<endl; // 獲取用戶輸入的字符串,並保存到strName變量 cin>>strName; // 通過string類型的length()函數獲取strName的長度 // 並判斷其長度是否小於6(字符串中是否少於6個字符) if(strName.length() < 6) { // 如果小於,則進行錯誤提示 cout<<"錯誤:用戶名至少包含6個字符"<<endl; }
在上面這段代碼中,我們首先定義了一個string類型的變量strName,用以保存用戶輸入的用戶名字符串,然後用cin獲取用戶輸入的字符串並保存到strName變量。接著再利用string類型的length()函數獲取字符串的長度,也就是strName中的字符個數。最後用if條件結構將其與我們要求的字符串長度6進行比較,如果不符合條件則進行錯誤提示。
知道更多:auto類型變量——根據初始值推斷真實的數據類型
在前面的章節中,我們介紹了C++中的多種數據類型:有表示整數的int類型也有表示浮點數的float類型;有表示單個字符的char類型也有表示字符串的string類型,這些意義不同用途各異的數據類型為我們定義變量來表示現實世界中的數據提供了豐富的選擇。但是,這些數據類型在使用上有一個共同的要求,那就是在定義變量表示數據時,我們必須先要知道所要表示的數據是什麼類型,到底是一個小數呢還是一串字符,然後才能據此確定到底是該使用float呢還是string。可是在開發實踐中,有時候我們並不能非常容易地確定一個變量應該具有的數據類型。比如,將某個復雜表達式作為初始值賦值給一個新定義的變量時,我們往往很難確定這個表達式的數據類型,從而無法確定變量應有的數據類型。為了解決這個問題,C++11為我們提供了auto關鍵字,使用它作為某個變量定義的數據類型,編譯器會根據這個變量的初始值,自動推斷出這個變量合理的數據類型而無需我們人為指定。例如:
auto x = 7; // 使用整數7對變量x進行初始化,x被推斷為int類型 auto y = 1.982; // 使用浮點數1.982對變量y進行初始化,y被推斷為double類型 Handler GetHandler(); // 使用GetHandler()函數的返回值對變量handler進行初始化 // handler被推斷為Handler類型 auto handler = GetHandler();
這裡我們在定義變量x的時候,並沒有指定其具體的數據類型,而是使用auto做為代替。這樣,編譯器在編譯這段代碼時,會根據7這個初始值自動推斷x的實際數據類型為int。同樣的道理,使用浮點數1.982進行初始化的變量y會被編譯器自動推斷為double類型;而最後的一個變量handler會被初始化為GetHandler()函數的返回值類型Handler。雖然auto關鍵字會根據初始值自動推斷變量的數據類型,但是,它的使用並不需要花費額外的編譯時間。有好處而又沒有額外的花費,auto關鍵字就像商場的免費大贈送,這樣的大便宜誰不喜歡呢?
實際上,可以把auto關鍵字看成是一個變量定義中的數據類型占位符,它占據了原來應該是具體數據類型的位置。而在編譯的時候,編譯器會根據這個變量的初始值,推斷出這個變量應有的具體數據類型,然後替換掉auto關鍵字,就成為一個普通的帶有具體數據類型的變量定義了。用auto關鍵字定義變量的形式跟一般的定義變量的形式並無二異,唯一的差別之處在於,用auto關鍵字定義變量時,變量必須有初始值:
auto 變量名 = 初始值表達式; // 賦值形式 // 或 auto 變量名{初始值表達式}; // 初始化列表形式
這樣,這個初始值表達式計算結果的數據類型將被編譯器推斷為變量的數據類型。
通常在定義變量時,如果我們很難准確地推斷它的數據類型,或者是這個變量的數據類型難於書寫,就可以使用auto作為變量的數據類型來定義變量,而真正的數據類型就交由編譯器去根據變量的初始值推斷得到好了。做這種苦力活,電腦要比人腦快多了。這樣做不僅省去了我們自己推斷數據類型的麻煩,避免了可能的人為錯誤,同時也可以達到簡化代碼的目的。例如:
template <typename T> // 數據類型vector<T>之後的“&”符號,表示其後所定義的變量是一個引用 // 引用是C++中一種訪問數據的特殊方式,在稍後的7.1小節中我們將詳細介紹 void printall(const vector<T>& v) { // 根據v.begin()的返回值類型自動推斷變量it的數據類型 for (auto it = v.begin(); it != v.end(); ++it) cout << *it << endl; }
為了表示同樣的意義,如果沒有auto關鍵字幫忙,我們不得不寫成下面這種繁瑣的形式:
template <typename T> void printall(const vector<T>& v) { for (typename vector<T>::const_iterator it = v.begin(); it != v.end(); ++it) cout << *it << endl; }
除了簡化代碼之外,auto關鍵字有時候甚至能夠幫助我們完成一些在C++11之前不可能完成的任務,成為一種必需。比如,在模板函數中,當一個變量的數據類型依賴於模板參數時,如果不使用auto關鍵字,將根本無法確定變量的數據類型,因為我們根本無法提前預知用戶使用何種數據類型作為模板參數來調用這個模板函數,從而也就無法確定這個變量的數據類型。但是使用auto關鍵字之後,一切難題都將迎刃而解。例如:
template <typename T,typename U> void mul(const T& t,const U& u) { // ... // 用auto關鍵字做數據類型,編譯器將根據u和t的實際數據類型, // 自動推斷變量tmp的數據類型 auto tmp = t*u; // ... }
在這裡,變量tmp的數據類型應該與模板參數T和U相乘結果的數據類型相同,也就是依賴於T和U的數據類型。對於程序員來說,在編寫這個模板函數的時候,模板參數T和U的類型尚未確定,這樣變量tmp的類型也就無法確定。所以,我們用auto關鍵字作為占位符,占據數據類型的位置,而真正的數據類型,則留待編譯器在最終編譯的時候,根據具體給定的模板參數T和U的類型而推斷得到。這樣,就把一件原來不可能的事情變成了可能。
使用auto關鍵字,可以根據變量的初始值自動推斷其數據類型,這樣就極大地方便了復雜數據類型變量的定義。但是,這種方式好是好,卻有一個缺點,那就是每次推斷得到的數據類型只能在定義變量的時候使用一次,無法保留下來繼續使用。好不容易推斷得到的數據類型只能使用一次,這就顯得有點不夠低碳環保了。而有時候,我們也需要這個推斷得到的數據能夠保留下來,從而可以重復使用以定義相同類型的多個變量。為了彌補這個缺點,C++11還提供了一個decltype關鍵字。它的使用語法形式如下:
typedef decltype(表達式) 用戶數據類型;
其中,decltype(表達式)是這個表達式的推斷數據類型(declared type),也就是這個表達式計算結果的數據類型。而typedef則是將這個數據類型定義為用戶自定義的數據類型,換句話說,也就是為這個推斷數據類型取一個名字,從而可以把它作為一個新的數據類型,用在定義變量、創建對象等任何需要數據類型的地方。例如,我們可以用decltype關鍵字改寫上面的例子:
template <typename T,typename U> void mul(const T& t,const U& u) { // ... // 用decltype得到t*u的數據類型, // 並用typedef關鍵字將其定義成一個新的數據類型M typedef decltype(t*u) M; // 用這個新的數據類型M定義指針變量(表示變量或函數地址的變量),創建M類型對象 M* tmp = nullptr; tmp = new M; // ... }
auto和decltype的作用有些相似,都可以推斷某個表達式的具體數據類型。但是,兩者的使用還是稍有差別。如果我們僅僅是想根據初始值確定一個變量合適的數據類型,那麼auto是最佳人選。而只有當我們需要推斷某個表達式的數據類型,並將其作為一種新的數據類型重復使用(比如,定義多個相同類型變量)或者單獨使用(比如,作為函數的返回值類型)時,我們才真正需要用到decltype。
[Chen1]確認
B
一、數據類型概述
數據:計算機能夠處理數值、文字、聲音、圖形、圖像等信息,均稱為數據。
數據類型:根據數據描述信息的含義,將數據分為不同的種類,對數據種類的區分規定,稱為數據類型。數據類型的不同,則在內存中的存儲結構也不同,占用空間也不同
VB的基本數據類型:
數值型數據 (主要數據類型) 日期型 字節型
貨幣型 邏輯型 字符串型 對象型 變體型
二、 數值數據類型
數值類型分為整數型和實數型兩大類。
1、整數型
整數型是指不帶小數點和指數符號的數。
按表示范圍整數型分為:整型、長整型
(1)整型(Integer,類型符%)
整型數在內存中占兩個字節(16位)
十進制整型數的取值范圍:-32768 ~ +32767
例如:15,-345,654%都是整數型。而45678%則會發生溢出錯誤。
(2)長整型(Long,類型符&)
長整數型在內存中占4個字節(32位)。
十進制長整型數的取值范圍:
-2147483648 ~ +2147483647
例如:123456,45678&都是長整數型。
2、實數型(浮點數或實型數)
實數型數據是指帶有小數部分的數。
注意:數12和數12.0對計算機來說是不同的,前者是整數(占2個字節),後者是浮點數(占4個字節)
實數型數據分為浮點數和定點數。
浮點數由三部分組成:符號,指數和尾數。
在VB中浮點數分為兩種:
單精度浮點數( Single )
雙精度浮點數( Double )
(1)單精度數(Single,類型符!)
在內存中占4個字節(32位),,有效數字:7位十進制數
取值范圍:負數 -3.402823E+38 ~ -1.401298E-45
正數 1.401298E-45 ~ 3.402823E+38
在計算機程序裡面不能有上標下標的寫法,所以乘冪采用的是一種稱為科學計數法的表達方法
這裡用E或者e表示10的次方(E/e大小寫都可以)
比如:1.401298E-45表示1.401298的10的負45次方
vb裡面可以這樣表示:8.96E-5
例:21e5(正號省略)表示:
21乘以10的5次方的一個單精度數
(2) 雙精度數(Double,類型符#)
Double類型數據在內存中占用8個字節(64位)
Double型可以精確到15或16位十進制數,即15或16位有效數字。
取值范圍:
負數: –1.797693134862316D+308 ~ -4.94065D-324
正數: 4.94065D-324 ~ 1.797693134862316D+308
比如17.88D5,表示它是一個雙精度數,表示17.88乘以10的5次方
這裡用D來表示10的次方
二、 貨幣型(Currency,類型符@)
主要用來表示貨幣值,在內存中占8個字節(64位);
整數部分為15位,可以精確到小數點後4位,第五位四捨五入;屬於定點實數
貨幣型數據的取值范圍:
-922337203685447. 5808 ......余下全文>>