Why is this ambiguity here?

Viewed 23788

Consider I have the following minimal code:

#include <boost/type_traits.hpp>

template<typename ptr_t>
struct TData
{
    typedef typename boost::remove_extent<ptr_t>::type value_type;
    ptr_t data;

    value_type & operator [] ( size_t id ) { return data[id]; }
    operator ptr_t & () { return data; }
};

int main( int argc, char ** argv )
{
    TData<float[100][100]> t;   
    t[1][1] = 5;
    return 0;
}

GNU C++ gives me the error:

test.cpp: In function 'int main(int, char**)':
test.cpp:16: error: ISO C++ says that these are ambiguous, even though the worst conversion for the first is better than the worst conversion for second:
test.cpp:9: note: candidate 1: typename boost::remove_extent<ptr_t>::type& TData<ptr_t>::operator[](size_t) [with ptr_t = float [100][100]]
test.cpp:16: note: candidate 2: operator[](float (*)[100], int) <built-in>

My questions are:

  1. Why GNU C++ gives the error, but Intel C++ compiler is not?
  2. Why changing operator[] to the following leads to compiling without errors?

    value_type & operator [] ( int id ) { return data[id]; }

Links to the C++ Standard are appreciated.


As I can see here are two conversion paths:

  1. (1)int to size_t and (2)operator[](size_t).
  2. (1)operator ptr_t&(), (2)int to size_t and (3)build-in operator[](size_t).
6 Answers
Related