const qualifier with function overloading

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include<iostream>
using namespace std;
class A{
    public:
        void fun(char *a) const
        {
            cout << "non-const fun() " << a << endl;
        }
        void fun(const char *a)
        {
            cout << "const fun() " << a << endl;
        }
};

int main()
{
    A b;
    const char *ptr = "Sample string 1";
    char *ptr1 = "Sample String 2";
    b.fun(ptr);
    b.fun(ptr1);
    return 0;
}

I am getting compilation error. Compiler says ambiguous function call. When const qualifier is removed from below line then it compiled successfully and work as expected.
 
void fun(char *a) const
Last edited on
It works if you use the same parameter type (const char*) for both functions. String literals give you a pointer to const data so you shouldn't really be using pointers to non-const in main anyway.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include<iostream>
using namespace std;
class A{
    public:
        void fun(const char *a) const
        {
            cout << "non-const fun() " << a << endl;
        }
        void fun(const char *a)
        {
            cout << "const fun() " << a << endl;
        }
};

int main()
{
    A b;
    const char *ptr = "Sample string 1";
    const char *ptr1 = "Sample String 2";
    b.fun(ptr);
    b.fun(ptr1);
    return 0;
}

Last edited on
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
#include <iostream>

struct A
{
    void fun( const char* ) const { std::cout << "A::fun( const char* ) const\n" ; }
    void fun( const char* ) { std::cout << "A::fun( const char* )\n" ; }

    void fun( char* ) const { std::cout << "A::fun( char* ) const\n" ; }
    void fun( char* ) { std::cout << "A::fun( char* )\n" ; }
};

int main()
{
    const A const_a {} ;
    A mutable_a {} ;

    const char const_cstr[10] = "const" ;
    char mutable_cstr[10] = "not const" ;

    const_a.fun(const_cstr) ; // A::fun( const char* ) const
    mutable_a.fun(const_cstr) ; // A::fun( const char* )

    const_a.fun(mutable_cstr) ; // A::fun( char* ) const
    mutable_a.fun(mutable_cstr) ; // A::fun( char* )
}

http://coliru.stacked-crooked.com/a/a8da7d3e0dd81e82
Then why do you even need to ask? You already have found a solution for yourself.

It's always a good idea to understand why something works. Otherwise there's a good chance that the "fix" works by accident and will break if you even breath on the code.

I hope that someone else will give a definitive answer. The error is at line 21. I may be wrong, but I seem to recall that the compiler is allowed to make only 1 implicit conversion to resolve a function call. So in this case, it can convert b to a const and call fun(char *) const or it can convert ptr1 to a const and call fun(const char*). Since it has to do one or the other, the call is ambiguous.
> the compiler is allowed to make only 1 implicit conversion to resolve a function call.

A standard conversion sequence can be combined with a user-defined conversion
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include <iostream>

struct A
{
    A( int v ) : value(v) {}
    A( const char* ) : value(7) {}
    int value ;
};

void foo( A a ) { std::cout << "foo( A{" << a.value << "} )\n" ; }

int main()
{
    foo( 'a' ) ;
    // 1. standard conversion: char => int
    // 2. user-defined conversion: int => A

    char cstr[5] {} ;
    foo( cstr ) ;
    // 1. standard conversion: array to pointer conversion ( char[5] => char* )
    // 2. standard conversion: qualification conversion ( char* => const char* )
    // 3. user-defined conversion: const char* => A
}

http://coliru.stacked-crooked.com/a/5240414aade4e790


> in this case, it can convert b to a const and call fun(char *) const
> or it can convert ptr1 to a const and call fun(const char*).
> Since it has to do one or the other, the call is ambiguous.

Yes. Neither one is a "better viable function" than the other.
dhayden and JLBorges, thanks for the explanation.
Topic archived. No new replies allowed.