2-10 彙總前面的學習經驗(第四章、第五章)(貳)

第五章   表達式(C++語言定義的操作符,使用內置類型的操作數)

一元操作符unary,如取地址操作符&,解引用操作符*

二元操作符binary,如加法操作符+,減法操作符-

5.1&5.2算數操作符、關係操作符、邏輯操作符

溢出:表達式的求值結果超出了其類型的表示範圍。

關係操作符和邏輯操作符使用算術或指針類型的操作數,並返回bool類型的值:&&與,||或

string s("Expression in c++ are composed by some data and control symbols");
string::iterator it = s.begin();
while(it != s.end() && !isspace(*it)){
      *it = toupper(*it);
      ++it;
}
cout << "convert the string to" << endl;

if(i < j < k)語句中的k與0、1相比較,關係操作符是從左開始進行計算

bool值本身可以進行if()語句的判斷,bool值爲真是1,爲假是0.

5.3位操作符bitwise operator

char是C/C++整型數據中比較古怪的一個,其它的如int/long/short等不指定signed/unsigned時都默認是signed,但char在標準中是unsigned

0UL  表示  無符號長整型0    unsigned long

1UL   表示   無符號長整型 1   unsigned long

如果不寫UL後綴,系統默認爲:int, 即,有符號整數。

1.數值常數有:整型常數、浮點常數;
2.只有數值常數纔有後綴說明;
3.數值常數後綴不區分字母大小寫。
(1)整型常數的表示形式有:十進制形式、以0開頭的八進制形式、以0x開頭的十六進制形式,無二進制形式。
整型常數默認是signed int的。
對整型常數進行類型轉換的後綴只有:u或U(unsigned)、l或L(long)、u/U與l/L的組合(如:ul、lu、Lu等)。例:100u; -123u; 0x123l;
(2)浮點常數的表示形式有:科學計數形式和小數點形式。
浮點常數默認是double的。
對浮點常數進行類型轉換的後綴只有:f或F(單精度浮點數)、l或L(長雙精度浮點數)。(注:因浮點型常數總是有符號的,故沒有u或U後綴)。例:1.23e5f; 1.23l; -123.45f;

位操作符:~ 位求反      << 左移    >>  右移   & 位與   ^ 位異或    | 位或

bitset<30>  bitset_quizl;

unsigned long int_quizl = 0;

bitset_quizl.set(27);使用bitset來進行賦值計算

邏輯與、邏輯或操作符采用成爲“短路求值”(short-circuit evaluation)的求值策略

輸入輸出標準庫(IO library)分別重載了位操作符 >> 和 << 用於輸入和輸出。

移位操作符具有中等優先級:其優先級比算術操作符低,高於關係操作符、賦值操作符、條件操作符

5.4賦值操作符

數組名是不可修改的左值,而下標和解引用操作符都返回左值。

賦值操作符的優先級低於  不等操作符      賦值操作符具有“右結合性”

5.5、5.6自增和自減操作符

儘量使用前自增操作:前置操作只需要加1後返回加1後的結果;後置操作符必須先保存操作數原來的值,以便返回未加1的值作爲操作結果。

後自增操作優先級 > 解引用操作

每一個變量都有一個內存位置,每一個內存位置都定義了可使用連字號(&)運算符訪問的地址,它表示了在內存中的一個地址。可以對指針進行四種算術運算:++、--、+、-

#include<iostream>
#include<string>
#include<vector>
using namespace std;

int main()
{
	vector<string*> spevc;

	//讀取vector對象
	string pv;
	while (cin >> pv) {
		string *tr = new string;    //指向string 的指針
		*tr = pv;
		spevc.push_back(tr);    //push_back必須兩個的類型相同  spevc爲指向string的指針,而tr也必須是指針
	}

	//輸出每個string 的內容及大小
	vector<string*>::iterator iter = spevc.begin();
	while (iter != spevc.end()) {
		cout << "every string is " << **iter << (**iter).size() << endl;    //第一個*解釋的是迭代器iterator的地址,第二個*解釋的是迭代器中元素的地址
		cout << "every string is " << *iter << endl;    //*iter的類型爲std::vector<string>::iterator類型
		iter++;
	}

	//釋放各個動態分配的string對象
	iter = spevc.begin();
	while (iter != spevc.end()) {
		delete *iter;
		iter++;
	}
	return 0;
}

iter -> empty()調用iter所指向的string對象的成員函數empty

iter++ -> empty()調用iter所指向的string對象的成員函數empty,並使iter加1

5.7、條件操作符

語法格式:cond ?expr1:expr2;cond爲條件判斷表達式,爲真時計算expr1。爲假時計算expr2。    二元判斷的最優選擇

int max = i > j

                    ?  i > k ? i : k

                    :  j > k ? j : k;

#include<iostream>
#include<vector>
using namespace std;

int main()
{
	int T;
	vector<int> s;
	while (cin >> T) {
		s.push_back(T);
	}

	for (vector<int>::iterator iter = s.begin(); iter != s.end(); iter++) {
		*(iter+1) = ((*iter > *(iter + 1)) ? *iter : *(iter + 1));
		cout << *(iter + 1) << endl;
	}
    return 0;
}

 

#include<iostream>
#include<vector>
using namespace std;

int main()
{
	vector<int> ivec(20, 1);
	;
	size_t a = 0;
	
	for (; a != ivec.size(); ++a) { //for語句中必須要有兩個分隔符,隔開三個語句
		
		if (a % 2 == 0) {
			ivec[a] = ivec[a] * 2;
			cout << ivec[a] << endl;
		}
		else
		{
			cout << ivec[a] << endl;
		}
		  
	}	
	return 0;
}
//  int iv, a = 0;
//  while (cin >> iv)
//		ivec.push_back(iv)
//  for (vector<int>::iterator i = ivec.begin(); i != ivec.end(); i++) {
//  if ((*i % 2) == 0) {
		//		*i = *i * 2;

5.8 sizeof () 操作符

      返回一個對象或類型名的長度,類型爲size_t  表達式的結果爲編譯時常量

      1、對 char 類型或值爲 char 類型的表達式做 sizeof 操作保證得 1。

      2、對引用類型做 sizeof 操作將返回存放此引用類型對象所需的內在空間大小。

      3、對指針做 sizeof 操作將返回存放指針所需的內在大小;注意,如果要獲取該指針所指向對象的大小,則必須對指針進行引用。 

      4、操作等效於將對其元素類型做 sizeof 操作的結果乘上數組元素的個數。

5.9 逗號操作符

      逗號表達式是一組由逗號分隔的表達式,這些表達式從左向右計算。逗號表達式的結果是其最右邊表達式的值。

5.10 優先級

       ++ 的優先級高於 * 操作符

       第二個規則有一個重要的例外:如果一個子表達式修改操作數的值,然後將該子表達式的結果用於另一個子表達式,這樣則是安全的。例如,*++iter 表達式的自增操作修改了 iter 的值,然後將 iter(修改後)的值用作 * 操作符的操作數。對於這個表達式或其他類似的表達式,其操作數的計算次序無關緊要。而爲了計算更復雜的表達式,改變操作數值的子表達式必須首先計算。這種方法很常用,不會產生什麼問題。

5.11 new 和 delete 表達式

        動態創建和釋放數組、單個對象等。

        定義變量時,必須指定其數據類型和名字。而動態創建對象時,只需指定其數據類型,而不必爲該對象命名。取而代之的是,new 表達式返回指向新創建對象的指針,

        對於類類型的對象,用該類的默認構造函數初始化,string類型等提供了默認構造函數;而內置類型的對象則無初始化。

         int *pi = new int();

         delete p;刪除語句後,p沒有定義,但是仍然存放了之前所指對象的地址。p所指向的內存已釋放,p不再有效,變爲懸垂指針。懸垂指針指向曾經存放對象的內存,但該對象已不存在。delete語句需要指向指針的對象。

         const int *pci = new const int(1024);

5.12 類型轉換

        隱式類型轉換:混合類型轉換相同類型;用作條件的表達式被轉換爲bool類型。

        最簡單的轉換爲整型提升:對於所有比 int 小的整型,包括 char、signed char、unsigned char、short 和 unsigned short,如果該類型的所有可能的值都能包容在 int 內,它們就會被提升爲 int 型,否則,它們將被提升爲 unsigned int。如果將 bool 值提升爲 int ,則 false 轉換爲 0,而 true 則轉換爲 1。

         在使用數組時,大多數情況下數組都會自動轉換爲指向第一個元素的指針;

         不將數組轉換爲指針的例外情況有:數組用作取地址(&)操作符的操作數或 sizeof 操作符的操作數時,或用數組對數組的引用進行初始化時,不會將數組轉換爲指針。

         指向任意數據類型的指針都可轉換爲 void* 類型;整型數值常量 0 可轉換爲任意指針類型

         while(cin >> s)其中,while循環條件爲bool類型的值,此時給出的卻是istream類類型的值,istream類型的值應該轉換爲bool類型。將istream類型轉換爲bool類型需要檢驗流的狀態。

          顯式轉換:強制類型轉換cast,static cast、dynamic cast、const cast、reinterpret cast

         dynamic_cast支持運行時識別指針或引用所指向的對象

         const_cast 將轉換掉表達式的 const 性質

                            const char *pc_str;

                             char *pc = string_copy(const_cast<char*>(pc_str)); 

         static_cast 編譯器隱式執行的任何類型轉換都可以顯式完成

         reinterpret_cast 通常爲操作數的位模式提供較低層次的重新解釋。

          舊式強制轉換符號有下列兩種形式:

           type (expr);     // Function-style cast notation

          (type) expr;      // C-language-style cast notation

           

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章