[英]STL style function to find the middle of an STL container
我是C ++的新手,我請求幫助來解決問題。
我正在編寫一個簡單的STL樣式函數,它應該返回序列的中間元素(向量,列表等)
這是我的函數,我嘗試使用迭代器的概念
template <class It, class T> It middle(It first, It last)
{
while(first!=last){
++first;
--last;
}
return first;
}
這是我的主要,試圖調用中間為一個向量的向量(我省略了包括)
int main() {
vector<int>vi;
int x;
cout<<"Enter vector elemets...";
while (cin>>x)
vi.push_back(x);
cout<<endl;
cin.clear();
cout<<"the vector is:"<<endl;
for(int i=0;i<vi.size();++i)
cout<<vi[i]<<" ";
cout<<endl;
vector<int>::iterator first=vi.begin();
vector<int>::iterator last=vi.end();
vector<int>::iterator ii=middle(first,last);
cout<<"The middle element of the vector is: "<<*ii<<endl;
}
使用g ++編譯時出現以下錯誤:
myex21-7.cpp:79: error: no matching function for call to ‘middle(__gnu_cxx::__normal_iterator<int*, std::vector<int, std::allocator<int> > >&, __gnu_cxx::__normal_iterator<int*, std::vector<int, std::allocator<int> > >&)’
有人可以給我一些解決方法嗎? 感謝您對高級潛行的任何幫助
怎么樣:
auto middle = container.begin();
std::advance(middle, container.size()/2);
如果您有C ++ 11可用, std::next
允許您在一行而不是兩行中執行相同的操作。
還要注意,在容器支持隨機訪問迭代器(例如, std::vector
或std::deque
)的情況下,這將是相對有效的(恆定復雜度而不是線性復雜度)。
除非這是一個練習,否則用std::next
來實現某些東西可能更簡單。 暫時忽略具有偶數元素的容器的特殊情況,您可以使用以下內容:
std::vector<SomeType> v = ....;
auto mid = std::next(v.begin(), v.size()/2);
至於代碼的問題, middle
函數模板有兩個參數:
template <class It, class T> It middle(It first, It last) { .... }
但是沒有辦法從函數參數中推導出第二個參數。 由於無論如何都不需要參數,您只需刪除它:
template <class It> It middle(It first, It last) { .... }
這里的其他答案很有趣,但它們需要訪問容器本身。 要成為真正的STL樣式,您應該使用迭代器范圍。 這是一個為隨機訪問迭代器提供高效處理的解決方案,但也適用於前向迭代器
// http://ideone.com/1MqtuG
#include <iterator>
template <typename ForwardIt>
ForwardIt DoMidpoint(ForwardIt first, ForwardIt last, std::forward_iterator_tag)
{
ForwardIt result = first;
// Try to increment the range by 2
bool sawOne = false;
// EDIT: Note improvements to this loop in the comments
while(first != last)
{
++first;
if (sawOne)
{
// If that succeeded, increment the result by 1
++result;
sawOne = false;
}
else
{
sawOne = true;
}
}
return result;
}
template <typename RandomAccessIt>
RandomAccessIt DoMidpoint(RandomAccessIt first, RandomAccessIt last, std::random_access_iterator_tag)
{
return first + (last - first)/2;
}
template <typename ForwardIt>
ForwardIt midpoint(ForwardIt first, ForwardIt last)
{
return DoMidpoint(first, last, typename std::iterator_traits<ForwardIt>::iterator_category());
}
STL中有幾種迭代器,vector具有隨機訪問權限,這意味着你可以通過中間元素得到迭代器
auto middle = v.begin() + v.size()/2;
假設first
和last
是容器的begin()
和end()
迭代器,那么:
Iterator middle = first;
std::advance( middle, std::distance( first, last ) / 2 );
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.