臨時對象的產生
- 臨時對象也叫做 無名對象,(使用pass by value的方式會引發copy的操作,于是產生一個臨時的對象),造成效率的負擔,但是可以可以制造一些臨時對象
- 在型別的后面 直接加上() 并可以指定初始數值,相當于調用型別的構造函數,但是不指定對象的名稱
- 臨時對象一般常用于 仿函數和算法搭配上
- 代碼如下所示? print<int>的臨時對象被傳入 for_each函數中起作用,當for_each結束的時候,臨時對象結束了他的生命
#include <vector>
#include <iostream>
#include <algorithm>template<typename T>
class print{
public:void operator()(const T&elem){ //operator 重載()std::cout <<elem << " ";}
};void print_function(int value){std::cout <<value << " ";
}int main(){int ia[6] = {0,1,2,3,4,5};std::vector<int>iv{ia,ia+6};std::for_each(iv.begin(),iv.end(),print<int>()); //使用模板類的方式
// std::for_each(iv.begin(),iv.end(), print_function);}
靜態常量整數成員在class內部 直接初始化
#include <vector>
#include <iostream>
#include <algorithm>template<typename T>
class print{
public:void operator()(const T&elem){ //operator 重載()std::cout <<elem << " ";}
};void print_function(int value){std::cout <<value << " ";
}template <typename T>
class testClass{
public:static const T static_const_data_i = 5;static T static_data_i;
};//對于模板中使用static變量初始化,這段代碼不能省略
template<typename T>
T testClass<T>::static_data_i = 0;int main(){testClass<int>temp;temp.static_data_i = 9;std::cout << testClass<int>::static_data_i << std::endl;std::cout << testClass<int>::static_const_data_i << std::endl;
}
遞增/遞減/解除引用 的運算符重載寫法
#include <vector>
#include <iostream>
#include <algorithm>class INT{friend std::ostream& operator<< (std::ostream& os,const INT& i);
public:INT(int i):m_i(i){};//prefix:increment and then fetchINT& operator++(){++(this->m_i); //隨著class的不同,這一行有不同的操作return *this;}const INT operator++(int){INT temp = *this;++(*this);return temp;}INT& operator--(){--(this->m_i);return *this;}const INT operator--(int){INT temp = *this;--(*this);return temp;}int & operator*() const{return (int &)m_i;}
private:int m_i;
};std::ostream& operator<<(std::ostream& os,const INT& i){os << '[' << i.m_i << ']' << " ";return os;
}int main(){INT I(5);std::cout << I++ ;// [5]std::cout << ++I; // [7]std::cout << I--; // [7]std::cout << --I; // [5]std::cout << *I; // 5
}
前閉后開 區間表示法
- STL算法需要使用一對迭代器(泛型指針)表示 區間,也就是操作的的范圍,使用[first.,last)來表示;實際的范圍是first 開始 到 last-1結束?
- last指代的是 最后一個元素的下一個位置?
- 使用的是 偏移一格 的標示法
template<class InputIterator,class T>
InputIterator find(InputIterator first,InputIterator last,const T& value){while(first != last && *first != value){++first;}return value;
}template<class InputIterator,class Function>
Function for_each(InputIterator first,InputIterator last,Function f){for (; first != last; ++first) {f(*first);}return f;
}

?函數回調 操作符( function call)
- 函數調用操作(也就是左括號和右括號)? 也可以被重載
- STL算法 提供了兩個版本,一個用于一般情況(比如按照遞增序列進行排序)? ;一個用于特殊情況(按照用戶指定的規則進行排序);用戶指定的規則 是通過函數進行制定的
- 先前 C語言時代 如果想將函數作為參數進行傳遞? 只能使用函數指針的方式
#include <vector>
#include <iostream>
#include <algorithm>int fcmp(const void* elem1,const void* elem2){const int* i1 = (const int*) elem1;const int* i2 = (const int*) elem2;if (*i1 < *i2){return -1;}else if(*i1 == *i2){return 0;}elsereturn 1;}int main(){int ia[10] = {32,92,67,58,10,4,25,52,59,54};for (int i = 0; i < 10; ++i) {std::cout << ia[i] << " ";}qsort(ia,sizeof(ia)/sizeof (int), sizeof (int),fcmp);std::cout << std::endl;for (int i = 0; i < 10; ++i) {std::cout << ia[i] << " ";}
}
- 函數指針有缺陷 無法維持自己的狀態? 也無法達到組件技術中的 可適配性,也就是無法再將 某些裝飾條件 加諸其上而改變其狀態
- 因此STL使用仿函數的形式實現了所謂的策略,仿函數類似于函數,比如針對某個類的進行operator()重載 就成為了仿函數,如果需要將其轉換為可配接的仿函數需要額外的努力
- 這個例子 缺乏 可配接能力 的體現? 將在第8章 詳述
#include <vector>
#include <iostream>
#include <algorithm>//由于將operator()重載了 因此plus成為了一個仿函數
template <class T>
struct plus{T operator()(const T& x,const T& y)const{return x+y;}
};//由于將operator()重載了 因此minus成為了一個仿函數
template <class T>
struct minus{T operator()(const T& x,const T& y)const{return x-y;}
};int main(){//產生仿函數對象plus<int>plus_obj;minus<int>minus_obj;//以下使用仿函數就像使用一般函數一樣std::cout << plus_obj(3,67) << std::endl;std::cout << minus_obj(67,3) << std::endl;//以下直接產生函數的臨時對象(第一對小括號) 并進行調用(第二隊小括號)//使用括號產生臨時對象std::cout << plus<int>()(3,67) <<std::endl;std::cout << minus<int>()(67,3) << std::endl;
}
參考鏈接
- c++類模板遇上static關鍵字_宿罪的博客-CSDN博客_static 模板
- c++中ostream類的超詳細說明 - 知乎