繁体   English   中英

c ++函数重载,表达式模板和命名空间

[英]c++ function overloading, expression templates and namespace

我正在开发一个基于表达式模板和运算符/函数重载的自动差异化工具。 例如,模板std :: max函数已成功重载:

namespace ead {
    ...
    template<class A>
    struct ExprWrap
    {
        inline
        operator A const& () const
        { return *static_cast<A const*>(this);}
    };

    class adnumber : public ExprWrap<adnumber>
    { ..... };

    template<typename L, typename R>
    class MaxExpr : public ExprWrap<MaxExpr<L,R> >{ ...... };

    // overloading std::max
    template<typename L, typename R>
    MaxExpr<L,R>
    max (ExprWrap<L> const& l, ExprWrap<R> const& r)
    {
        return MaxExpr<L,R>(l,r); // return an expression
    }
    ...
}

但在如下代码中

using namespace std;
using namespace ead;

adnumber x,y,z;
z = max(x,y);      // call std::max

如果省略了名称空间,则使用std :: ,对于其他一些函数,使用ead :: 是否有强制编译器始终选择ead :: namespace的技巧,例如,对于max函数? (请不要使用C ++ 11特性)为什么编译器认为std :: max是更好的匹配?
好吧,我知道在函数名称之前编写ead ::并不是什么大问题,但我想保存用户不要打字。

考虑std::max实例化产生:

std::max(ead::adnumber, ead::number);

这是一个比你的max签名更好的匹配(它是完全匹配)。 因此它将被调用。 你唯一的出路是限定调用,因为你不能通过SFINAE使std::max实例化失败,或者使你的ead::max成为一个完全通用的ead::max(T, T) 第二次尝试会使调用变得模棱两可。

假设adnumber是在名称空间ead定义的用户定义类型(即, 不是 typedef ),则函数max()应该搜索名称空间eadstd 当然, std::max()是一个完美的匹配,即它赢得了重载adnumber ,除非adnumber碰巧是某个类型T ExprWrap<T>typedef 这是一个简单的示例,显示了不同的情况:

#include <iostream>

namespace ead
{
    template <typename T> struct ExprWrap {};

    template <typename T>
    void max(ExprWrap<T> const&) { std::cout << "ead::max()\n"; }

    typedef int builtin;
    struct other {};
    typedef ExprWrap<int> instance;
    struct derived: ExprWrap<int> {};
}

namespace foo
{
    template <typename T>
    void max(T const&) { std::cout << "foo::max()\n"; }
}

int main()
{
    using namespace foo;
    using namespace ead;

    ead::builtin  b;
    ead::other    o;
    ead::instance i;
    ead::derived  d;

    max(b);
    max(o);
    max(i);
    max(d);
}

这应该打印

foo::max()
foo::max()
ead::max()
foo::max()

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM