c++函数模板问题

essential C++课后题2.5,重载函数max(),源码链接

2.6是让使用template来重写2.5,我按照书上答案,运行出错,书上的源码链接

看报错信息应该重载有歧义

In function 'int main()':
Line 37: error: call of overloaded 'max(int, int)' is ambiguous
compilation terminated due to -Wfatal-errors.

把max函数名改成max_new函数名运行成功改动后代码

请问我如果不改函数名,如何能够运行正确呢?

阅读 2.4k
3 个回答

你声明的max与<algorithm>里的template <class T> const T& max( const T& a, const T& b );构成了重载。
编译器报模糊调用的错误是因为调用max时编译器认为这“两个重载一样好”。

避免使用using namespace std;就能解决这个问题,这也是被广泛接受的最佳实践。

另:
去掉using namespace std;后,编译器在39行处会报模糊调用的错误。这是因为通过argument-dependent lookup(这里最外层的max的实际参数是std::string)找到了std::max,构成重载。解决方案可以是用::max(...)来调用全局域的max

修改后代码

可以使用命名空间把你自己实现的函数放入一个mynamespace的命名空间,然后后面的代码显示地制定命名空间mynamespace::max即可,代码如下:

#include <iostream>
#include <string>
#include <algorithm>
#include <vector>
namespace mynamespace{
    template <typename Type>
    inline Type max(Type t1,Type t2)
    {
        return t1 > t2 ? t1 : t2;
    }
}
template <typename elemType>
inline elemType max(const std::vector<elemType> &vec)
{
    return *max_element(vec.begin(),vec.end());
}

template <typename arrayType>
inline arrayType max(const arrayType *parray,int size)
{
    return *std::max_element(parray,parray + size);
}

int main()
{
    int iarray[]={12,70,2,169,1,5,29};
    std::vector<int> ivec(iarray,iarray + 7);

    float farray[]={2.5,24.8,18.7,4.1,23.9};
    std::vector<float> fvec(farray,farray + 5);

    std::string sarray[]={"we","were","her","pride","of","ten"};
    std::vector<std::string> svec(sarray,sarray + 6);



    int imax=mynamespace::max(max(ivec),max(iarray,7));
    float fmax=mynamespace::max(max(fvec),max(farray,5));
    std::string smax=mynamespace::max(max(svec),max(sarray,6));

    std::cout << "imax should be 169 -- found: "<<imax<<'\n'
         << "fmax should be 24.8 -- found: "<<fmax<<'\n'
         << "smax should be were -- found: "<<smax<<'\n';
    return 0;
}
撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
宣传栏