What does this error message mean?
error: call of overloaded ‘setval(int)’ is ambiguous huge.cpp:18: note: candidates are: void huge::setval(unsigned int) huge.cpp:28: note: void huge::setval(const char*)
My code looks like this:
#include <iostream> #define BYTES 8 using namespace std ; class huge { private: unsigned char data[BYTES]; public: void setval(unsigned int); void setval(const char *); }; void huge::setval(unsigned int t) { for(int i = 0; i< BYTES ; i++) { data[i] = t; t = t >> 1; } } void huge::setval(const char *s) { for(int i = 0; i< BYTES ; i++) data[i] = s[i]; } int main() { huge p; p.setval(0); return 0; }
A call to an overloaded function can be ambiguous in one of the following two ways: *The arguments mentioned in the function where it is called do not match the arguments at the point where the function is called. *The same function is defined more than one time in the same program.
You cannot override one virtual function with two or more ambiguous virtual functions. This can happen in a derived class that inherits from two nonvirtual bases that are derived from a virtual base class.
The function call operator, when overloaded, does not modify how functions are called. Rather, it modifies how the operator is to be interpreted when applied to objects of a given type.
Function Overloading in C++When a function name is overloaded with different jobs it is called Function Overloading. In Function Overloading “Function” name should be the same and the arguments should be different. Function overloading can be considered as an example of a polymorphism feature in C++.
The literal 0
has two meanings in C++.
On the one hand, it is an integer with the value 0.
On the other hand, it is a null-pointer constant.
As your setval
function can accept either an int
or a char*
, the compiler can not decide which overload you meant.
The easiest solution is to just cast the 0
to the right type.
Another option is to ensure the int
overload is preferred, for example by making the other one a template:
class huge { private: unsigned char data[BYTES]; public: void setval(unsigned int); template <class T> void setval(const T *); // not implemented template <> void setval(const char*); };
The solution is very simple if we consider the type of the constant value, which should be "unsigned int" instead of "int".
Instead of:
setval(0)
Use:
setval(0u)
The suffix "u" tell the compiler this is a unsigned integer. Then, no conversion would be needed, and the call will be unambiguous.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With