qiezi的学习园地

AS/C/C++/D/Java/JS/Python/Ruby

  C++博客 :: 首页 :: 新随笔 ::  ::  :: 管理 ::
CSDN上看到有人问能否实现一个效率较高的max函数,效率接近于宏,于是自动动手写了一个。

由于max宏在判断不同类型时,能够返回大的那个类型(表示范围大),所以只能使用模板来进行返回类型的推导。

在VC8上打开O2或Ox优化选项,测试结果是与宏效率相等。

全部实现如下:

#include <typeinfo>
#include 
<cassert>
#include 
<windows.h>
#include 
<iostream>


template 
<class T, class U, bool B>
struct BigType
{
    typedef T result;
};

template 
<class T, class U>
struct BigType<T, U, false>
{
    typedef U result;
};



template 
<class T, class U>
struct Type
{
    typedef typename BigType
<T, U, (sizeof(T) > sizeof(U))>::result BigType;
};

template 
<class T>
struct Type<T, double>
{
    typedef 
double BigType;
};

template 
<class T>
struct Type<double, T>
{
    typedef 
double BigType;
};


template 
<class T>
struct Type<T, float>
{
    typedef 
float BigType;
};

template 
<class T>
struct Type<float, T>
{
    typedef 
float BigType;
};


template 
<>
struct Type<doublefloat>
{
    typedef 
double BigType;
};

template 
<>
struct Type<floatdouble>
{
    typedef 
double BigType;
};



template 
<class T, class U>
typename Type
<T, U>::BigType MaX (const T& t, const U& u)
{
    typedef typename Type
<T, U>::BigType ResultType;
    
return ResultType(t > u ? t : u); // 原为return (ResultType)t > u ? t : u;
}

int main ()
{
    assert (typeid(MaX(
12)) == typeid(int));
    assert (MaX(
12== 2);

    assert (typeid(MaX(
12.5)) == typeid(double));
    assert (MaX(
12.5== 2.5);

    assert (typeid(MaX(
1, (float)2.5)) == typeid(float));
    assert (MaX(
1, (float)2.5== 2.5);

    assert (typeid(MaX((
double)2, (float)2.5)) == typeid(double));
    assert (MaX((
double)2, (float)2.5== 2.5);

    assert (typeid(MaX((
long)2, (float)2.5)) == typeid(float));
    assert (MaX((
long)2, (float)2.5== 2.5);

    assert (typeid(MaX((
long)2, (short)2)) == typeid(long));
    assert (MaX((
long)2, (short)2== 2);

    assert (typeid(MaX((
float)2, (__int64)2)) == typeid(float));
    assert (MaX((
float)2, (__int64)2== 2);

    assert (std::
string("hello"< "world");
    assert (typeid(MaX(std::
string("hello"), "world")) == typeid(std::string));
    assert (MaX(std::
string("hello"), "world"== "world");

    assert (typeid(MaX(std::
string("world"), "hello")) == typeid(std::string));
    assert (MaX(std::
string("hello"), "world"== "world");



    
// 测试数,需定义在循环外,防止编译器优化掉无意义的循环
    __int64 test = 0;
    
long start = GetTickCount();
    
for (int i=0; i<1000000000++i)
    {
        test 
+= MaX(i, (__int64)i);
    }
    
// test必须被使用,否则编译器视为无用数据,会被优化掉
    std::cout << test << std::endl;
    std::cout 
<< (GetTickCount() - start) << std::endl;

    test 
= 0;
    start 
= GetTickCount();
    
for (int i=0; i<1000000000++i)
    {
        test 
+= max(i, (__int64)i);
    }
    std::cout 
<< test << std::endl;
    std::cout 
<< (GetTickCount() - start) << std::endl;

    
return 0;
}
posted on 2005-12-12 10:45 qiezi 阅读(1902) 评论(7)  编辑 收藏 引用 所属分类: C++

评论

# re: 自己写的一个max函数 2005-12-12 12:43 芋头
c++0x中提到了auto/typeof关键字,如果实现了,就不用写这么麻烦了。按c++ 0x keynote中描述的,应该可以写成这样:
template <class T, class U>
typeof(t > u ? t : u) max (const T& t, const U& u)
{
return t > u ? t : u;
}

不过目前还没有编译器支持。g++编译器支持的typeof不能从函数参数中这样取类型,变通了一下:
template <class T, class U>
typeof(T() > U() ? T() : U()) MaX (const T& t, const U& u)
{
return t > u ? t : u;
}

结果编译时,提示出这个:
test.cpp: In function &acirc;€&#732;__typeof__ (((T() > U()) ? T() : U())) MaX(const T&, const U&) [with T = int, U = int]&acirc;€&#8482;:
test.cpp:8: internal compiler error: in write_type, at cp/mangle.c:1646
Please submit a full bug report,
with preprocessed source if appropriate.
See <URL:http://bugzilla.redhat.com/bugzilla> for instructions.
Preprocessed source stored into /tmp/ccdZk5dN.out file, please attach this to your bugreport.

看来属于编译器的一个BUG。
  回复  更多评论
  

# re: 自己写的一个max函数 2005-12-13 21:02 芋头
loki中有一个泛型的MIN、MAX函数实现,使用了typelist以及相关的模板,主要是Conversion模板。  回复  更多评论
  

# re: 自己写的一个max函数 2005-12-14 13:49 小明
其实不同类型的max比较,没有多少实际的意义吧。

比较实用的还是强制转化一下,然后用std::max  回复  更多评论
  

# re: 自己写的一个max函数 2005-12-14 13:59 芋头
max宏就不需要转换,这个宏至今还在使用的一个原因就是,暂时还找不到完全替代它的函数实现。就算是用泛型实现了,基于编译效率考虑,很多人还是愿意使用宏。

类型转换因为太麻烦了,所以不是人人都愿意做。C++很多隐式类型转换就证明了,很多人不愿意显式转换类型。。。  回复  更多评论
  

# re: 自己写的一个max函数 2006-10-09 23:31 冬天¤不回来
问你个问题.我经常看别人说"宏",到底是什么意思?  回复  更多评论
  

# re: 自己写的一个max函数 2006-10-10 00:10 qiezi
宏就是macro,再讲下去我也说不清了。。  回复  更多评论
  

# re: 自己写的一个max函数 2006-12-20 20:12 pengkuny
倒是要用用看  回复  更多评论
  


标题  
姓名  
主页
验证码 *
内容(提交失败后,可以通过“恢复上次提交”恢复刚刚提交的内容)  
  登录  使用高级评论  新用户注册  返回页首  恢复上次提交      
[使用Ctrl+Enter键可以直接提交]
相关链接:
网站导航: