web-dev-qa-db-ja.com

項目がstd :: vectorに存在するかどうかを調べる方法は?

私がしたいのは、要素がベクトル内に存在するかどうかをチェックすることだけなので、それぞれの場合に対処できます。

if ( item_present )
   do_this();
else
   do_that();
559
Joan Venge

std::findから <algorithm> を使用できます。

#include <vector>
vector<int> vec; 
//can have other data types instead of int but must same datatype as item 
std::find(vec.begin(), vec.end(), item) != vec.end()

これはブール値を返します(存在する場合はtrue、それ以外の場合はfalse)。あなたの例では:

#include <algorithm>
#include <vector>

if ( std::find(vec.begin(), vec.end(), item) != vec.end() )
   do_this();
else
   do_that();
835
MSN

他の人が言っているように、STLの find または find_if 関数を使ってください。ただし、非常に大きなベクトルを検索しているためにパフォーマンスに影響がある場合は、ベクトルを並べ替えてから binary_searchlower_bound 、または upper_bound のアルゴリズムを使用することをお勧めします。

104
Brian Neal

Stlのアルゴリズムヘッダからfindを使用してください。int型でその使用方法を説明しました。同等かどうかを比較できるのであれば、好きな型を使用できます(カスタムクラスに必要な場合はoverload ==)。

#include <algorithm>
#include <vector>

using namespace std;
int main()
{   
    typedef vector<int> IntContainer;
    typedef IntContainer::iterator IntIterator;

    IntContainer vw;

    //...

    // find 5
    IntIterator i = find(vw.begin(), vw.end(), 5);

    if (i != vw.end()) {
        // found it
    } else {
        // doesn't exist
    }

    return 0;
}
46
m-sharp

ベクトルが順序付けされていない場合は、MSNが提案した方法を使用してください。

if(std::find(vector.begin(), vector.end(), item)!=vector.end()){
      // Found the item
}

ベクトルが順序付けられている場合は、binary_searchメソッドを使用してください。

if(binary_search(vector.begin(), vector.end(), item)){
     // Found the item
}

二分探索はO(log n)の最悪の場合の性能をもたらし、これは最初のアプローチよりもはるかに効率的です。二分検索を使用するには、qsortを使用してベクトルが順序付けられていることを確認します。

36
Bin Feng

私はこのようなものを使います...

#include <algorithm>


template <typename T> 
const bool Contains( std::vector<T>& Vec, const T& Element ) 
{
    if (std::find(Vec.begin(), Vec.end(), Element) != Vec.end())
        return true;

    return false;
}

if (Contains(vector,item))
   blah
else
   blah

...そのようにそれは実際に明確で読みやすいです。 (明らかにあなたは複数の場所でテンプレートを再利用することができます)。

19
Andy Krouwel

これはどのコンテナにも使える関数です。

template <class Container> 
const bool contains(const Container& container, const typename Container::value_type& element) 
{
    return std::find(container.begin(), container.end(), element) != container.end();
}

コンテナからvalue_typeを抽出できるため、1つのテンプレートパラメータを使用しなくても済むことに注意してください。 Container::value_type従属名 であるため、typenameが必要です。

11

たくさんの検索をするのであれば、それに適したSTLコンテナがあることを忘れないでください。私はあなたのアプリケーションが何であるかわかりませんが、std :: mapのような連想コンテナは考慮する価値があるかもしれません。

他に理由がない限り、std :: vectorが最適なコンテナです。値による検索がそのような理由になることがあります。

10
David Thornley

C++ 11ではany_ofを使うことができます。例えばそれがvector<string> v;であれば:

if (any_of(v.begin(), v.end(), bind2nd(equal_to<string>(), item)))
   do_this();
else
   do_that();
10
Deqing

STLの find 関数を使います。

find_if 関数もあることを覚えておいてください。これはあなたの検索がもっと複​​雑な場合、すなわち要素を探しているのではなく、例えば要素があるかどうかを調べたい場合に使用できます。これは特定の条件、たとえば "abc"で始まる文字列を満たします。 (find_ifは最初のそのような要素を指すイテレータをあなたに与えるでしょう)。

8
Frank

Boostでは any_of_equal を使うことができる。

#include <boost/algorithm/cxx11/any_of.hpp>

bool item_present = boost::algorithm::any_of_equal(vector, element);
7
Mikhail

あなたはこのコードを試すことができます:

#include <algorithm>
#include <vector>

// You can use class, struct or primitive data type for Item
struct Item {
    //Some fields
};
typedef std::vector<Item> ItemVector;
typedef ItemVector::iterator ItemIterator;
//...
ItemVector vtItem;
//... (init data for vtItem)
Item itemToFind;
//...

ItemIterator itemItr;
itemItr = std::find(vtItem.begin(), vtItem.end(), itemToFind);
if (itemItr != vtItem.end()) {
    // Item found
    // doThis()
}
else {
    // Item not found
    // doThat()
}
5
TrungTN

find名前空間、つまりstd::findにある std 関数を使用できます。 std::find関数に、検索したいベクトルからbeginおよびendイテレータを渡し、探している要素とともに、結果のイテレータをベクトルの末尾と比較して、一致するかどうかを確認します。

std::find(vector.begin(), vector.end(), item) != vector.end()

他のイテレータと同様に、そのイテレータを参照解除して通常どおり使用することもできます。

3
TankorSmash

あなたもcountを使うことができます。ベクトル内に存在するアイテムの数を返します。

int t=count(vec.begin(),vec.end(),item);
3
Aditya

C++演算子を使用した別のサンプル.

#include <vector>
#include <algorithm>
#include <stdexcept>

template<typename T>
inline static bool operator ==(const std::vector<T>& v, const T& elem)
{
  return (std::find(v.begin(), v.end(), elem) != v.end());
}

template<typename T>
inline static bool operator !=(const std::vector<T>& v, const T& elem)
{
  return (std::find(v.begin(), v.end(), elem) == v.end());
}

enum CODEC_ID {
  CODEC_ID_AAC,
  CODEC_ID_AC3,
  CODEC_ID_H262,
  CODEC_ID_H263,
  CODEC_ID_H264,
  CODEC_ID_H265,
  CODEC_ID_MAX
};

void main()
{
  CODEC_ID codec = CODEC_ID_H264;
  std::vector<CODEC_ID> codec_list;

  codec_list.reserve(CODEC_ID_MAX);
  codec_list.Push_back(CODEC_ID_AAC);
  codec_list.Push_back(CODEC_ID_AC3);
  codec_list.Push_back(CODEC_ID_H262);
  codec_list.Push_back(CODEC_ID_H263);
  codec_list.Push_back(CODEC_ID_H264);
  codec_list.Push_back(CODEC_ID_H265);

  if (codec_list != codec)
  {
    throw std::runtime_error("codec not found!");
  }

  if (codec_list == codec)
  {
    throw std::logic_error("codec has been found!");
  }
}

ベクトルの中で文字列を見つけたい場合は、

    struct isEqual
{
    isEqual(const std::string& s): m_s(s)
    {}

    bool operator()(OIDV* l)
    {
        return l->oid == m_s;
    }

    std::string m_s;
};
struct OIDV
{
    string oid;
//else
};
VecOidv::iterator itFind=find_if(vecOidv.begin(),vecOidv.end(),isEqual(szTmp));
2
Gank
template <typename T> bool IsInVector(T what, std::vector<T> * vec)
{
    if(std::find(vec->begin(),vec->end(),what)!=vec->end())
        return true;
    return false;
}
1
user3157855

(C++ 17以上):

std::searchも使用できます

これは一連の要素を検索するのにも役立ちます。

#include <algorithm>
#include <iostream>
#include <vector>

template <typename Container>
bool search_vector(const Container& vec, const Container& searchvec)
{
    return std::search(vec.begin(), vec.end(), searchvec.begin(), searchvec.end()) != vec.end();
}

int main()
{
     std::vector<int> v = {2,4,6,8};

     //THIS WORKS. SEARCHING ONLY ONE ELEMENT.
     std::vector<int> searchVector1 = {2};
     if(search_vector(v,searchVector1))
         std::cout<<"searchVector1 found"<<std::endl;
     else
         std::cout<<"searchVector1 not found"<<std::endl;

     //THIS WORKS, AS THE ELEMENTS ARE SEQUENTIAL.
     std::vector<int> searchVector2 = {6,8};
     if(search_vector(v,searchVector2))
         std::cout<<"searchVector2 found"<<std::endl;
     else
         std::cout<<"searchVector2 not found"<<std::endl;

     //THIS WILL NOT WORK, AS THE ELEMENTS ARE NOT SEQUENTIAL.
     std::vector<int> searchVector3 = {8,6};
     if(search_vector(v,searchVector3))
         std::cout<<"searchVector3 found"<<std::endl;
     else
         std::cout<<"searchVector3 not found"<<std::endl;
}

また、いくつかの検索アルゴリズムを渡す柔軟性があります。こちらを参照してください。

https://en.cppreference.com/w/cpp/algorithm/search

0
Naidu