代码之家  ›  专栏  ›  技术社区  ›  Chen Li

`在函数参数中键入“alias<char[n]>{}`vs`char[n]{}”

  •  8
  • Chen Li  · 技术社区  · 6 年前
    • 环境:x86-64 铿锵声 小精灵

    函数定义:

    void foo(const char*) {}
    
    1. foo(char[16]{}); //houston, there is a problem!
    2. foo(type_alias<char[16]>{}); //compile happily

    type_alias 很简单:

    template<typename T>
    using type_alias = T;
    

    live demon


    如评论所述, case 1 无法编译while case 2 罐头。

    我知道 alias declarations 具有 using 不是文本替换(如 #define )它是这个类型的同义词。

    但我还是不知道该如何解释这种情况。然后我给 海湾合作委员会 try :

    prog.cc: In function 'int main()':
    prog.cc:11:7: error: expected primary-expression before 'char'
       foo(char[16]{});
           ^~~~
    prog.cc:12:7: error: taking address of temporary array
       foo(type_alias<char[16]>{});
           ^~~~~~~~~~~~~~~~~~~~~~
    

    啊, 海湾合作委员会 却给了我一个错误!然后我用两个编译器的不同版本编译它:

    • 铿锵声 的错误消息 案例1 是:

    prog.cc:11:11:错误:对于函数样式转换或类型构造,应为“(”

    foo(char[16]{});
          ~~~~^
    
    • 铿锵声 案例2 通过。

    • 海湾合作委员会 这两个案子都不能通过竞争。的错误消息 案例1 案例2 已在上面列出。

    BTW,用于 铿锵声 ,我还测试了 pedantic-errors ,但没有改变。


    问题:

    • 对于 案例2 : 铿锵声 , 海湾合作委员会 ,谁符合标准?有什么标准(语言律师)规范吗?
    • 对于 案例1 :谁的错误消息更正确(IOW,符合标准)?

    更新

    作为VTT的评论, 案例1 ,应该是 foo(const char[16]{}); . 为这个错误道歉。

    但是 铿锵声 可以编译 foo(type_alias<char[16]>{}); . 好像是虫子?

    1 回复  |  直到 6 年前
        1
  •  7
  •   YSC    6 年前

    好, type_alias<cv T>{} 相当于 (cv T){} ,而不是 cv T{} . 当 T 是一个数组:

    foo((const char[16]){});              // OK
    foo(type_alias<const char[16]>{});    // OK
    
    foo(const type_alias<char>[16]{});    // KO
    foo(const char[16]{});                // KO
    

    演示: https://wandbox.org/permlink/KGf3HVqN3USq6yy8


    案例2:Clang,GCC,谁符合标准?有什么标准(语言律师)规范吗?

    都是,都接受 foo(type_alias<char>[16]{}) ,但是海湾合作委员会 警告 你就知道了 -Werror ,此警告将变为错误;)。