在程式中使用STL(第7章)(條款43)
阿新 • • 發佈:2021-01-10
條款43:演算法呼叫優先於手寫的迴圈
有三個理由
效率:演算法通常比程式設計師自己寫的迴圈效率更高;
正確性:自己寫迴圈比使用演算法更容易出錯;
可維護性:使用演算法的程式碼通常比手寫迴圈的程式碼更加簡潔明瞭;
書中的例子
void dequeTest() { deque<int> dq{2, 3, 4}; dq.push_back(5); dq.push_front(1); auto idq = dq.insert(dq.cbegin(), 0); // 注意,插入後返回插入節點的迭代器 idq = dq.insert(dq.cend(), 6); // 注意,插入後返回插入節點的迭代器 int arr[]{11, 12, 13, 14, 15}; // 測試用資料 const int N = 5; // 不使用演算法的例子,需要訊息維護迭代器的有效性 auto initer = dq.begin(); for (int i = 0; i < N; ++i) { initer = dq.insert(initer, arr[i] + 10); ++initer; } // 使用演算法的例子 // 1)將陣列依次插入到deque後面 std::copy(arr, arr + N, std::back_inserter(dq)); // 2)將陣列按照原來的順序依次+10後插入deque前面,採用lambda表示式實現 std::transform(std::begin(arr), std::end(arr), std::inserter(dq, dq.begin()), [](int x) { return x + 10; }); // lamada表示式 // 3)將陣列按照原來的順序依次+10後插入deque前面,採用bind 標準函式物件實現 std::transform(std::begin(arr), std::end(arr), std::inserter(dq, dq.begin()), std::bind(std::plus<int>(), std::placeholders::_1, 10)); // bind標準函式物件 return; }
輸出:
書中還舉了個例子,有些場景下使用迴圈更清晰,不過作者出版樹的時候C++11還沒有面世,因此那個例子是合理的,現在有lambda,書中那個例子也可以用演算法優雅的完成,程式碼如下
void dequeTest() { // 想要表明在一次迭代中完成什麼工作,則使用迴圈比演算法更為清晰 std::vector<int> vec{1, 2, 3, 4, 5, 6, 7, 8, 9}; int lowbound = 4; int upperbound = 6; auto iter = vec.begin(); for (; iter != vec.end(); ++iter) { if (*iter > lowbound && *iter < upperbound) { break; // *iter == 5 } } // 然而新版的C++也不是如此了,以前做法確實比較麻煩,還需要寫個函式物件,或者採用其他方式,現在有lambda auto i = std::find_if(vec.begin(), vec.end(), [=](int e) { return e > lowbound && e < upperbound; }); return; }