指针和整数的模糊重载?
Ambiguous overload of pointer and integer?
以下重载函数,
void foo(const void*)
{
printf("first");
}
void foo(unsigned int)
{
printf("second");
}
在这种情况下,生成一个不明确的重载
foo((int)0);
但不是这个
foo((int)1);
为什么?是因为人们还在用NULL
吗?在没有显式转换的情况下,解决该问题的最佳方法是什么?
(我在 Ubuntu 18.04 上使用 GCC 8.3.0-C++11 进行编译)
编辑
正如你们中的一些人在评论中指出的那样,(int)0
实际上编译没有错误(至少在 GCC 8.3.0 上,使用 C++11 std)。我遇到的问题只是 foo(0)
,我现在明白为什么了。
文字 0
在 C 和 C++ 中具有特殊含义,因为它也是一个空指针文字。这就是 NULL
的工作原理。
如果您使用字面量调用函数,而不是 foo(0)
,您可以使用 foo(0u)
,这是有效的,因为 0u
已经具有类型 unsigned int
,所以调用整数重载不需要转换。如果您使用整数变量调用 foo
,则不应有任何冲突。 (演示 here)
如评论中所述,(int)0
不应引起任何冲突,GCC 8.3 doesn't produce any error with foo((int)0)
in C++11 mode, but does in C++98 mode (and so does clang). As mentioned by @StoryTeller-UnslanderMonica in the comments, this is caused by a defect http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#903 未追溯应用于 C++98。
在像您这样的情况下,您通常可以使用 SFINAE 或 requires()
帮助自己。这是一个想法,但其他解决方案也是可能的:
void foo(void const*)
{
printf("first");
}
void foo(auto a)
requires(
std::is_integral_v<decltype(a)> &&
!std::is_same_v<decltype(NULL), decltype(a)>
)
{
printf("second");
}
但是,NULL
在 c++ 中通常不会出现问题。
以下重载函数,
void foo(const void*)
{
printf("first");
}
void foo(unsigned int)
{
printf("second");
}
在这种情况下,生成一个不明确的重载
foo((int)0);
但不是这个
foo((int)1);
为什么?是因为人们还在用NULL
吗?在没有显式转换的情况下,解决该问题的最佳方法是什么?
(我在 Ubuntu 18.04 上使用 GCC 8.3.0-C++11 进行编译)
编辑
正如你们中的一些人在评论中指出的那样,(int)0
实际上编译没有错误(至少在 GCC 8.3.0 上,使用 C++11 std)。我遇到的问题只是 foo(0)
,我现在明白为什么了。
文字 0
在 C 和 C++ 中具有特殊含义,因为它也是一个空指针文字。这就是 NULL
的工作原理。
如果您使用字面量调用函数,而不是 foo(0)
,您可以使用 foo(0u)
,这是有效的,因为 0u
已经具有类型 unsigned int
,所以调用整数重载不需要转换。如果您使用整数变量调用 foo
,则不应有任何冲突。 (演示 here)
如评论中所述,(int)0
不应引起任何冲突,GCC 8.3 doesn't produce any error with foo((int)0)
in C++11 mode, but does in C++98 mode (and so does clang). As mentioned by @StoryTeller-UnslanderMonica in the comments, this is caused by a defect http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#903 未追溯应用于 C++98。
在像您这样的情况下,您通常可以使用 SFINAE 或 requires()
帮助自己。这是一个想法,但其他解决方案也是可能的:
void foo(void const*)
{
printf("first");
}
void foo(auto a)
requires(
std::is_integral_v<decltype(a)> &&
!std::is_same_v<decltype(NULL), decltype(a)>
)
{
printf("second");
}
但是,NULL
在 c++ 中通常不会出现问题。