mardi 5 décembre 2017

Clang ambiguity with custom conversion operator

I've been developing kind of adapter class, when encountered problem under clang. When both conversion operators for lvalue-reference and rvalue reference are defined you get an ambiguity compilation error trying to move from your class (when such code should be fine, as

operator const T& () const&

is allowed only for lvalues AFAIK). I've reproduced error with simple example:

#include <string>

class StringDecorator
{
public:
  StringDecorator()
  : m_string( "String data here" )
  {}

  operator const std::string& () const& // lvalue only
  {
    return m_string;
  }

  operator std::string&& () && // rvalue only
  {
    return std::move( m_string );
  }

private:
    std::string m_string;
};

void func( const std::string& ) {}
void func( std::string&& ) {}

int main(int argc, char** argv)
{
  StringDecorator my_string;

  func( my_string ); // fine, operator std::string&& not allowed
  func( std::move( my_string ) ); // error "ambiguous function call"
}

Compiles fine on gcc 4.9+, fails on any clang version. So the question: is there any workaround? Is my understanding of const& function modifier right?

Aucun commentaire:

Enregistrer un commentaire