为什么函数含糊不清

时间:2015-09-07 16:16:41

标签: c++

在g ++(v4.7.3)上编译示例代码时,出现错误:

$ g++ -std=c++11 te2b.cc
te2b.cc: In function ‘int main(int, char**)’:
te2b.cc:17:19: warning: ISO C++ says that these are ambiguous, even though the worst conversion for the first is better than the worst conversion for the second: [enabled by default]
te2b.cc:10:6: note: candidate 1: void notify(std::string, int)
te2b.cc:7:6: note: candidate 2: void notify(const char*, ...)

以下是示例代码。不明白为什么不明确:编译器应该知道将notify()中的main()的调用映射到第一个声明。 void notify(const char *fmt, ...)

#include <vector>
#include <iostream>
#include <unordered_map>
#include <stdarg.h>
using namespace std;
char notifyBuf[0x100000] = "\x06\x00\x00\x00" "notify""s";
void notify(const char *fmt, ...) {
    //....
}
void notify(string s, int maxSize = 0) {
    if (maxSize && (maxSize < s.size())) {
        s.erase(maxSize);
    }
    notify("%s\n", s.c_str());
}
int main(int argc, char *argv[]) {
    notify("%5d ", 89);    
    return 0;
}

有什么想法吗?感谢。

1 个答案:

答案 0 :(得分:3)

§13.3.3[over.match.best] / p2:

  

鉴于这些定义,可行函数F1被定义为比另一个可行函数更好的函数   F2如果对于所有参数i,ICS i (F1)不是比ICS i (F2)更差的转换序列,然后

     

(1.3) - 对于某些参数j,ICS j (F1)是比ICS j (F2)更好的转换序列,或者,如果不是,[...]

给定函数调用notify("%5d ", 89);和两个重载:

void notify(const char*, ...);   // F1
void notify(std::string, int);   // F2

编译器为F1的参数设置了以下隐式转换序列:

  • ICS 0 (F1) - 标准转换序列(指针转换的数组)
  • ICS 1 (F1) - 省略号转换序列

以及F2的参数的以下隐式转换序列集:

  • ICS 0 (F2) - 用户定义的转换序列(通过构造函数)
  • ICS 1 (F2) - 标准转换序列(身份转换)

因为ICS 0 (F1)优于ICS 0 (F2),但ICS 1 (F2)依次为优于ICS 1 (F1),编译器无法在两者之间进行选择。*

*§13.3.3.2[over.ics.rank] / p2:

  

比较隐式转换序列的基本形式(如13.3.3.1中所定义):

     

- 标准转换序列(13.3.3.1.1)是比用户定义的转换序列或省略号转换序列更好的转换序列,并且

     

- 用户定义的转换序列(13.3.3.1.2)是比省略号转换序列(13.3.3.1.3)更好的转换序列。