本文介紹c++語言中進行查詢操作的高效模板。
提起查詢,最先想到的應該就是find函式,find函式的定義如下:
templateinputiterator find(inputiterator first, inputiterator last, const t& val);
簡單的說,就是確定查詢的起始點和終止點及查詢的內容,返回第一次找到的位置。
還是給乙個例子:
查詢陣列中數字5第一次出現的位置。
int a = ;
int* index = find(a, a + 5, 5);
cout << (int)(index - a) << endl;
如果查不到,返回的是指向陣列後乙個位置的指標。如在例子中,將查詢值改為11,則輸出值為5。
如果是對於string的操作,查詢'a'第一次出現的位置。
string s = "hello";
int index = s.find('a');
結果index直接就是第一次出現的位置下標。
如果是對於vector或者list等結構,呼叫find函式方法與陣列類似,但所有的引數由陣列中的指標變為相應的迭代器。
其他的如find_first_of, find_last_of, find_first_not_of 用法都與find類似,只是意義稍有不同。
對於上面的find函式,只能以乙個等於特定的值作為查詢條件,而不能以乙個範圍作為限定條件。
下面介紹find_if函式,可以理解為find函式的泛型,其定義如下:
templateinputiterator find_if(inputiterator first, inputiterator last, predicate pred);
這個函式也是有三個引數,前兩個引數也是表示find的起始和終止位置,第三個引數一般為乙個布林型別的函式,用於給出篩選條件,滿足條件的返回true。該函式的返回值的情形與find是相同的。
find函式給過陣列和string的例子,這裡就給乙個vector的例子。查詢偶數。
vectora = ;
auto res = find_if(a.begin(), a.end(), (int x) -> bool );
結果res是引用第乙個滿足條件的元素的迭代器。如果查詢不到則返回last的迭代器。與find函式相同。
bool ret(int x)
呼叫find_if時直接使用函式名即可。
auto res = find_if(a.begin(), a.end(), ret });
上面介紹的find / find_if函式可以用來做什麼?指定元素定位,判斷是否存在指定元素,這些都是可以的。
但經常還可以看到有很多人把它用來提取滿足條件的元素,或者對滿足條件的元素進行計數,而且有很多論壇的帖子也是這麼教的。不可否認這可以做,但效率不一定比for迴圈高,而且**不一定比直接for迴圈簡單。可以用一些更優化的函式模板來做這些問題。
對滿足條件的元素計數,可以使用count / count_if函式。其中count_if是count的泛型。
count函式的函式引數與find函式是相同的,只是返回值是滿足條件的元素個數,例子就不給了。
count_if函式的引數與find_if函式相同,只是返回值是滿足條件元素個數,給乙個和上面相似的例子。求偶數的個數。
vectora = ;
auto res = count_if(a.begin(), a.end(), (int x) -> bool );
對於提取所有滿足條件的元素,可以使用copy_if函式。
還是上面的例子,提取所有偶數。
vectora = ;
vectorb(a.size());
auto res = copy_if(a.begin(), a.end(), b.begin(), (int x) -> bool );
b.resize(distance(b.begin(), res));
for (int x : b)
cout << ' ' << x;
可以看到相比於前面的find_if和count_if。copy_if函式多了第三個引數,表示copy到的位置。其餘引數意義仍相同。
在copy的時候做了處理,先預設b的大小為a,然後resize改變b的大小。resize中使用了函式distance,即計算兩個迭代器之間的元素個數差。res表示copy到的陣列(例子中為b)的拷貝結束點的後一位的迭代器,即copy_if函式的返回值。
還有函式remove_copy_if,是拷貝不滿足條件的元素。即原集合與copy_if拷貝後的集合的差集。remove_copy_if與copy_if函式的引數及返回值意義相同。
如果要求是查詢所有滿足條件的結果並做替換。此時就要用到replace / replace_if函式。replace_if是replace的泛型。
用法都是相似的,只給乙個replace_if函式的例子。
還是上面的例子,將所有偶數替換為1。
vectora = ;
replace_if(a.begin(), a.end(), (int x) -> bool , 1);
可以看出copy_if函式前兩個引數也是指示位置,第三個引數是判斷條件,第四個引數是替換後的值。這個函式返回值為void。
從上面這麼多的例子可以看出,對於查詢所要做的各種操作,我們不一定全部要依賴於乙個find函式來實現,這樣無論是實現的開銷還是**量都是大的。c++語言已經為我們提供了這些好用的函式,我們為什麼不用呢?
本文所涉及**均在visual studio 2015中通過。部分**如lambda表示式,需要支援c++ 11標準的編譯器,如最新版g++及vs2012及以上版本等。
快速開發平台 web快速開發平台 Jxstar介紹
jxstar支援面向業務構件的開發思想,支援各種標準應用構件 行業應用構件 整合應用構件開發 維護,最大限度的提高業務構件的重用,提高軟體企業的資產價值與市場競爭力。通過平台配置完成大部分開發工作量,提高開發效率與開發質量 規範企業軟體開發過程,降低軟體後期維護的時間和成本 通過平台積累可重用軟體構...
C 開發快速匯入ssl安全證書
首先需要引入命名空間 system.security.cryptography.x509certificates 首先需要了解 參考 使用指定的 storename 和 storelocation 值初始化 x509store 類的新例項。參考 特別注意以下引數 成員名稱 說明addressbook...
php快速開發
tablename table gift 表名 colarray array 0 array giftname 1,禮品名稱 text 45 1 array count 1,換禮積分 text 2 array createdate 0,建立日期 now 3 array orderby 1,排序 te...