Question

I'm trying to run some tests on the elements of a map with gtest in the following way:

typedef std::map< std::string, std::vector< std::string > > maptype;

static maptype generateMapOfElements() {...}

class MyTest : public TestWithParam< maptype::value_type > {
...
}

TEST_P(MyTest , my_first_test) { .. }

INSTANTIATE_TEST_CASE_P(test_prefix,
                        MyTest,
                        ValuesIn( generateMapOfElements() ) ); // <- problem

the problem seems that instantiating pair::swap is creating problems since the map's key is a const string (full log below)

1>C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\utility(48): error C2678: binary '=' : no operator found which takes a left-hand operand of type 'const std::string' (or there is no acceptable conversion)
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\xstring(912): could be 'std::basic_string<_Elem,_Traits,_Alloc> &std::basic_string<_Elem,_Traits,_Alloc>::operator =(std::basic_string<_Elem,_Traits,_Alloc> &&) throw()'
1>          with
1>          [
1>              _Elem=char,
1>              _Traits=std::char_traits<char>,
1>              _Alloc=std::allocator<char>
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\xstring(969): or       'std::basic_string<_Elem,_Traits,_Alloc> &std::basic_string<_Elem,_Traits,_Alloc>::operator =(const std::basic_string<_Elem,_Traits,_Alloc> &)'
1>          with
1>          [
1>              _Elem=char,
1>              _Traits=std::char_traits<char>,
1>              _Alloc=std::allocator<char>
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\xstring(987): or       'std::basic_string<_Elem,_Traits,_Alloc> &std::basic_string<_Elem,_Traits,_Alloc>::operator =(const _Elem *)'
1>          with
1>          [
1>              _Elem=char,
1>              _Traits=std::char_traits<char>,
1>              _Alloc=std::allocator<char>
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\xstring(992): or       'std::basic_string<_Elem,_Traits,_Alloc> &std::basic_string<_Elem,_Traits,_Alloc>::operator =(_Elem)'
1>          with
1>          [
1>              _Elem=char,
1>              _Traits=std::char_traits<char>,
1>              _Alloc=std::allocator<char>
1>          ]
1>          while trying to match the argument list '(const std::string, const std::basic_string<_Elem,_Traits,_Alloc>)'
1>          with
1>          [
1>              _Elem=char,
1>              _Traits=std::char_traits<char>,
1>              _Alloc=std::allocator<char>
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\utility(56) : see reference to function template instantiation 'void std::swap<_Ty>(_Ty &,_Ty &)' being compiled
1>          with
1>          [
1>              _Ty=std::string
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\utility(107) : see reference to function template instantiation 'void std::_Swap_adl<_Ty1>(_Ty &,_Ty &)' being compiled
1>          with
1>          [
1>              _Ty1=std::string,
1>              _Ty=std::string
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\utility(104) : while compiling class template member function 'void std::pair<_Ty1,_Ty2>::swap(std::pair<_Ty1,_Ty2> &)'
1>          with
1>          [
1>              _Ty1=const std::string,
1>              _Ty2=std::vector<testing::internal::string>
1>          ]
1>          C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\utility(211) : see reference to function template instantiation 'void std::pair<_Ty1,_Ty2>::swap(std::pair<_Ty1,_Ty2> &)' being compiled
1>          with
1>          [
1>              _Ty1=const std::string,
1>              _Ty2=std::vector<testing::internal::string>
1>          ]
1>          C:\dir\my_test.cpp(251) : see reference to class template instantiation 'std::pair<_Ty1,_Ty2>' being compiled
1>          with
1>          [
1>              _Ty1=const std::string,
1>              _Ty2=std::vector<testing::internal::string>
1>          ]
Was it helpful?

Solution

The ValuesIn function returns a generator that retains a copy of the values, and that copy is stored in a vector. (Why does it store a copy? Because in general, it can't rely on the original value source to remain valid for the lifetime of the test.) One of the requirements for vector is that its element type must be assignable (C++03, §23.1/3). However, as you've already noticed, map::value_type is pair<const Key, T>. The const key type prevents the type from being assignable.

Instead of a map<string, vector<string>> from your generator function, you might consider returning a vector<pair<string, vector<string>>>.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top