如何在向量中找到5个最大元素的索引?

时间:2012-09-17 20:19:40

标签: c++ stl

如何在向量中找到5个最大元素的索引? 例如std::vector<int>如何找到5个最大值但不改变原始向量的索引?

5 个答案:

答案 0 :(得分:12)

std::partial_sort( v.begin(), v.begin()+5, v.end() )以某种方式对向量进行排序,即对5个最小值进行排序并在v的开头进行排序。剩下的就是未分类。

既然你想要索引并保留原文:
使用0..n-1中的数字填充一个新向量,并提供一个v[a] > v[b]代替a > b的比较函数:

struct Comp{
    Comp( const vector<int>& v ) : _v(v) {}
    bool operator ()(int a, int b) { return _v[a] > _v[b]; }
    const vector<int>& _v;
}

vector<int> vx;
vx.resize(v.size());
for( int i= 0; i<v.size(); ++i ) vx[i]= i;
partial_sort( vx.begin(), vx.begin()+5, vx.end(), Comp(v) );

vx[0..4]包含索引。

答案 1 :(得分:2)

您可以从原始矢量制作副本,并使用STL nth_element中的专用算法对其进行部分排序:

bool cmp (int i,int j) { return (i<j); }    
int main () {
      vector<int> myvector;
      vector<int>::iterator it;

      // set some values:
      for (int i=1; i<10; i++) myvector.push_back(i);   // 1 2 3 4 5 6 7 8 9

      random_shuffle (myvector.begin(), myvector.end());

      // using default comparison (operator <):
      std::vector<int> copy_of_orig = myvector;
      nth_element (copy_of_orig.begin(), copy_of_orig.begin()+5, copy_of_orig.end(), cmp);
      // Display the first five biggest elts.
      for (int i = 0; i < 5; ++i)
        std::cout << copy_of_orig[i] << std::endl;
}

答案 2 :(得分:1)

1解决方案:

解决方案是O(n),其中n是被检查的载体中的元素数。

创建长度为5的向量迭代器的队列,用NULL初始化 读取正在检查的向量元素和push_back索引{想法是在前面或后面推送新索引,这取决于读取的新元素数据是小于后面索引的数据还是大于前面索引的数据,如果已经在dequeue中的数据是NULL,那么无论你是push_front还是push_back,都没关系}。这将保持从前到后排序的出队。

如果正在读取的新数据大于前端数据,则移除后部并向前推动当前数据的迭代器;否则什么都不做

在迭代结束时,dequeue将包含前五个元素的迭代器。

答案 3 :(得分:1)

可能会有更优雅的方式,但我现在很难找到它。你可以这样做(未经测试,所以不能保证它开箱即用,特别是在角落的情况下,但它应该):

std::array<int, 5> indices = {-1,-1,-1,-1,-1};//-1 used as invalid index for cases where myVec.size()<5
for(int i = 0; i < myVec.size(); ++i)
{
    for(int j = 0; j < 5; ++j)
        if((indices[j] == - 1) || (myVec[i] > myVec[indices[j]]))
        {
            std::copy_backward(indices.begin() + j, indices.end() - 1, indices.end());
            indices[j] = i;
            break;
        }
}

它保留了5个最大元素的列表。对于向量的每个元素,它将以最大元素开始,测试新元素是否更大,如果是,则将索引向下移动并插入为第一个,否则测试第二大元素,依此类推。不会修改vector并在O(n)中以非常低的开销运行。

如果你不能使用C ++ 11,你总是可以使用std::vector(或int[5],如果你真的想要)而不是std::array

答案 4 :(得分:0)

你需要做这样的事情:

  int largestNumbers [5]{0, 0, 0, 0, 0};

  for each( const int i in data ){
  {
    for (int index = 0; index < 5; index++){
       if (i > largestNumber[index]){
          largestNumber[index] = i;
       }
     }
  }