Why does the compiler prefer f(const void*) to f(const std::string &)?
up vote
39
down vote
favorite
Consider the following piece of code:
#include <iostream>
#include <string>
// void f(const char *) { std::cout << "const char *"; } // <-- comment on purpose
void f(const std::string &) { std::cout << "const std::string &"; }
void f(const void *) { std::cout << "const void *"; }
int main()
{
f("hello");
std::cout << std::endl;
}
I compiled this program using g++ (Ubuntu 6.5.0-1ubuntu1~16.04) 6.5.0 20181026
:
$ g++ -std=c++11 strings_1.cpp -Wall
$ ./a.out
const void *
Note that the comment is there on purpose to test, otherwise the compiler uses f(const char *)
.
So, why does the compiler pick f(const void*)
over f(const std::string &)
?
c++ stdstring string-literals function-overloading overload-resolution
New contributor
|
show 2 more comments
up vote
39
down vote
favorite
Consider the following piece of code:
#include <iostream>
#include <string>
// void f(const char *) { std::cout << "const char *"; } // <-- comment on purpose
void f(const std::string &) { std::cout << "const std::string &"; }
void f(const void *) { std::cout << "const void *"; }
int main()
{
f("hello");
std::cout << std::endl;
}
I compiled this program using g++ (Ubuntu 6.5.0-1ubuntu1~16.04) 6.5.0 20181026
:
$ g++ -std=c++11 strings_1.cpp -Wall
$ ./a.out
const void *
Note that the comment is there on purpose to test, otherwise the compiler uses f(const char *)
.
So, why does the compiler pick f(const void*)
over f(const std::string &)
?
c++ stdstring string-literals function-overloading overload-resolution
New contributor
4
Here's the relevant part of the standard: eel.is/c++draft/over.ics.rank#2.1
– geza
Nov 17 at 18:53
@geza awesome. I was looking for it, thanks.
– omar
Nov 17 at 18:56
The overloading resolution rule here is simple and unchanged in the many C++ versions.
– curiousguy
Nov 17 at 19:01
4
Well, a string literal is not anstd::string
, it's a static array ofchar
s, which decays to a pointer to its first character. This behavior is inherited from C which never had something likestd::string
, but ample amounts of code handling strings nonetheless.
– cmaster
Nov 17 at 21:49
1
If you specifically want astd::string
literal you can achieve that by adding as
behind the literal. This is a user-defined literal which is available since C++14. en.cppreference.com/w/cpp/string/basic_string/operator%22%22s
– henje
Nov 18 at 10:56
|
show 2 more comments
up vote
39
down vote
favorite
up vote
39
down vote
favorite
Consider the following piece of code:
#include <iostream>
#include <string>
// void f(const char *) { std::cout << "const char *"; } // <-- comment on purpose
void f(const std::string &) { std::cout << "const std::string &"; }
void f(const void *) { std::cout << "const void *"; }
int main()
{
f("hello");
std::cout << std::endl;
}
I compiled this program using g++ (Ubuntu 6.5.0-1ubuntu1~16.04) 6.5.0 20181026
:
$ g++ -std=c++11 strings_1.cpp -Wall
$ ./a.out
const void *
Note that the comment is there on purpose to test, otherwise the compiler uses f(const char *)
.
So, why does the compiler pick f(const void*)
over f(const std::string &)
?
c++ stdstring string-literals function-overloading overload-resolution
New contributor
Consider the following piece of code:
#include <iostream>
#include <string>
// void f(const char *) { std::cout << "const char *"; } // <-- comment on purpose
void f(const std::string &) { std::cout << "const std::string &"; }
void f(const void *) { std::cout << "const void *"; }
int main()
{
f("hello");
std::cout << std::endl;
}
I compiled this program using g++ (Ubuntu 6.5.0-1ubuntu1~16.04) 6.5.0 20181026
:
$ g++ -std=c++11 strings_1.cpp -Wall
$ ./a.out
const void *
Note that the comment is there on purpose to test, otherwise the compiler uses f(const char *)
.
So, why does the compiler pick f(const void*)
over f(const std::string &)
?
c++ stdstring string-literals function-overloading overload-resolution
c++ stdstring string-literals function-overloading overload-resolution
New contributor
New contributor
edited Nov 17 at 19:00
curiousguy
4,47722940
4,47722940
New contributor
asked Nov 17 at 18:27
omar
25919
25919
New contributor
New contributor
4
Here's the relevant part of the standard: eel.is/c++draft/over.ics.rank#2.1
– geza
Nov 17 at 18:53
@geza awesome. I was looking for it, thanks.
– omar
Nov 17 at 18:56
The overloading resolution rule here is simple and unchanged in the many C++ versions.
– curiousguy
Nov 17 at 19:01
4
Well, a string literal is not anstd::string
, it's a static array ofchar
s, which decays to a pointer to its first character. This behavior is inherited from C which never had something likestd::string
, but ample amounts of code handling strings nonetheless.
– cmaster
Nov 17 at 21:49
1
If you specifically want astd::string
literal you can achieve that by adding as
behind the literal. This is a user-defined literal which is available since C++14. en.cppreference.com/w/cpp/string/basic_string/operator%22%22s
– henje
Nov 18 at 10:56
|
show 2 more comments
4
Here's the relevant part of the standard: eel.is/c++draft/over.ics.rank#2.1
– geza
Nov 17 at 18:53
@geza awesome. I was looking for it, thanks.
– omar
Nov 17 at 18:56
The overloading resolution rule here is simple and unchanged in the many C++ versions.
– curiousguy
Nov 17 at 19:01
4
Well, a string literal is not anstd::string
, it's a static array ofchar
s, which decays to a pointer to its first character. This behavior is inherited from C which never had something likestd::string
, but ample amounts of code handling strings nonetheless.
– cmaster
Nov 17 at 21:49
1
If you specifically want astd::string
literal you can achieve that by adding as
behind the literal. This is a user-defined literal which is available since C++14. en.cppreference.com/w/cpp/string/basic_string/operator%22%22s
– henje
Nov 18 at 10:56
4
4
Here's the relevant part of the standard: eel.is/c++draft/over.ics.rank#2.1
– geza
Nov 17 at 18:53
Here's the relevant part of the standard: eel.is/c++draft/over.ics.rank#2.1
– geza
Nov 17 at 18:53
@geza awesome. I was looking for it, thanks.
– omar
Nov 17 at 18:56
@geza awesome. I was looking for it, thanks.
– omar
Nov 17 at 18:56
The overloading resolution rule here is simple and unchanged in the many C++ versions.
– curiousguy
Nov 17 at 19:01
The overloading resolution rule here is simple and unchanged in the many C++ versions.
– curiousguy
Nov 17 at 19:01
4
4
Well, a string literal is not an
std::string
, it's a static array of char
s, which decays to a pointer to its first character. This behavior is inherited from C which never had something like std::string
, but ample amounts of code handling strings nonetheless.– cmaster
Nov 17 at 21:49
Well, a string literal is not an
std::string
, it's a static array of char
s, which decays to a pointer to its first character. This behavior is inherited from C which never had something like std::string
, but ample amounts of code handling strings nonetheless.– cmaster
Nov 17 at 21:49
1
1
If you specifically want a
std::string
literal you can achieve that by adding a s
behind the literal. This is a user-defined literal which is available since C++14. en.cppreference.com/w/cpp/string/basic_string/operator%22%22s– henje
Nov 18 at 10:56
If you specifically want a
std::string
literal you can achieve that by adding a s
behind the literal. This is a user-defined literal which is available since C++14. en.cppreference.com/w/cpp/string/basic_string/operator%22%22s– henje
Nov 18 at 10:56
|
show 2 more comments
1 Answer
1
active
oldest
votes
up vote
48
down vote
accepted
Converting to a std::string
requires a "user defined conversion".
Converting to void const*
does not.
User defined conversions are ordered behind built in ones.
add a comment |
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
up vote
48
down vote
accepted
Converting to a std::string
requires a "user defined conversion".
Converting to void const*
does not.
User defined conversions are ordered behind built in ones.
add a comment |
up vote
48
down vote
accepted
Converting to a std::string
requires a "user defined conversion".
Converting to void const*
does not.
User defined conversions are ordered behind built in ones.
add a comment |
up vote
48
down vote
accepted
up vote
48
down vote
accepted
Converting to a std::string
requires a "user defined conversion".
Converting to void const*
does not.
User defined conversions are ordered behind built in ones.
Converting to a std::string
requires a "user defined conversion".
Converting to void const*
does not.
User defined conversions are ordered behind built in ones.
answered Nov 17 at 18:40
Yakk - Adam Nevraumont
178k19185363
178k19185363
add a comment |
add a comment |
omar is a new contributor. Be nice, and check out our Code of Conduct.
omar is a new contributor. Be nice, and check out our Code of Conduct.
omar is a new contributor. Be nice, and check out our Code of Conduct.
omar is a new contributor. Be nice, and check out our Code of Conduct.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53354226%2fwhy-does-the-compiler-prefer-fconst-void-to-fconst-stdstring%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
4
Here's the relevant part of the standard: eel.is/c++draft/over.ics.rank#2.1
– geza
Nov 17 at 18:53
@geza awesome. I was looking for it, thanks.
– omar
Nov 17 at 18:56
The overloading resolution rule here is simple and unchanged in the many C++ versions.
– curiousguy
Nov 17 at 19:01
4
Well, a string literal is not an
std::string
, it's a static array ofchar
s, which decays to a pointer to its first character. This behavior is inherited from C which never had something likestd::string
, but ample amounts of code handling strings nonetheless.– cmaster
Nov 17 at 21:49
1
If you specifically want a
std::string
literal you can achieve that by adding as
behind the literal. This is a user-defined literal which is available since C++14. en.cppreference.com/w/cpp/string/basic_string/operator%22%22s– henje
Nov 18 at 10:56