V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
linux40
V2EX  ›  C

为什么这样写 g++会在 noexcept 那里报 expression cannot be used as a function 这样的错误?

  •  
  •   linux40 · 2015-08-29 20:50:07 +08:00 · 1396 次点击
    这是一个创建于 3381 天前的主题,其中的信息可能已经有所发展或是发生改变。
    11 条回复    2015-08-30 19:17:01 +08:00
    firemiles
        1
    firemiles  
       2015-08-29 22:16:48 +08:00   ❤️ 1
    expression 必须要能在编译时计算,函数在运行时计算,你在 expression 内嵌入了两个函数,所以这个 expression 也变成了 function ,而 noexcept 规定只能用于 expression 。
    linux40
        2
    linux40  
    OP
       2015-08-29 23:09:06 +08:00
    @firemiles 这个 noexcept 不会对表达式求值啊,为什么不会变成判断 T1 这个类型的接受一个 Other1 的构造函数抛不抛异常?
    linux40
        3
    linux40  
    OP
       2015-08-29 23:11:02 +08:00
    @firemiles 对于同类型可以,别的类型就不行了。。。
    linux40
        4
    linux40  
    OP
       2015-08-29 23:15:58 +08:00
    @firemiles 但是 operator=的话,其他类型可以。。。
    bazingaterry
        5
    bazingaterry  
       2015-08-30 00:21:47 +08:00
    打开 gist 竟然提示

    ![]( )
    firemiles
        6
    firemiles  
       2015-08-30 09:20:10 +08:00
    @linux40
    template <typename T1, typename T2>
    struct pair {
    //...
    template <typename Other1, typename Other2> constexpr
    pair (Other1 &&o1, Other2 &&o2 ) noexcept (
    noexcept (first (forward<Other1>(o1 ))) &&
    noexcept (second (forward<Other2>(o2 )))
    ): first (forward<Other1>(o1 )), second (forward<Other2>(o2 )) {}
    //...
    };

    forward<Ohter1>(o1 ) 应该不是一个 constexpr 吧,这样不是进行了一次函数调用吗
    firemiles
        7
    firemiles  
       2015-08-30 09:48:51 +08:00
    @linux40 不好意思,测试了一下 noexcept 里调用函数确实可以,之前对 noexcept 理解有点问题。
    firemiles
        8
    firemiles  
       2015-08-30 09:57:19 +08:00
    @linux40 我用 clang++可以编译通过,你换个编译器试试吧
    linux40
        9
    linux40  
    OP
       2015-08-30 13:07:20 +08:00
    @firemiles 是吗,那 g++就有我 3 、 4 楼说的情况,而 clang++就可以正常进行二楼所说的判断?
    firemiles
        10
    firemiles  
       2015-08-30 14:19:14 +08:00
    @linux40

    template <typename T1, typename T2>
    struct pair {
    //...
    template <typename Other1, typename Other2> constexpr
    pair (Other1 &&o1, Other2 &&o2 ) noexcept (
    noexcept (T1 (std::forward<Other1>(o1 ))) &&
    noexcept (T2 (std::forward<Other2>(o2 )))
    ): first (std::forward<Other1>(o1 )), second (std::forward<Other2>(o2 )) {}
    //...
    T1 first;
    T2 second;
    };
    int main ()
    {
    pair<int, double> a (1, 1.2 );
    }


    我试着这么写可以通过编译,不知道满不满足你的要求,那两个 first 和 second 在 noexcept 里的我改成了 T1 和 T2 。
    linux40
        11
    linux40  
    OP
       2015-08-30 19:17:01 +08:00
    @firemiles 满足。。。
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   955 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 27ms · UTC 22:53 · PVG 06:53 · LAX 14:53 · JFK 17:53
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.