【C++算法】冒泡排序及其优化

关于冒泡排序算法,这里就不多说了。

简单说一下优化,一般的冒泡排序是单向的,而其优化之一就是双向冒泡:正向扫描获取最大值,反向扫描获取最小值。

由于C++11以前的实现有点复杂,在此就基于C++11新特性来实现,并写成库的形式。

编译环境:C++11

代码实现如下:

#include <type_traits> // std::declval

template<typename _Tp>
void swap(_Tp &a1, _Tp &a2)
{
    _Tp tmp = a1;
    a1 = a2;
    a2 = tmp;
}

template<typename _Tp>
struct Comparator
{
    int operator()(const _Tp &arg1, const _Tp &arg2) const
    {
        if(arg1 < arg2) return 1;
        if(arg2 < arg1) return -1;
        return 0;
    }
};

typedef unsigned long size_type;

/// 普通冒泡排序
/// 范围:[beg, end)
/// 参数限定:支持前向迭代
template<typename _ForwardIter,
         typename _Compare = Comparator<decltype(*std::declval<_ForwardIter>())>>
void fsort(_ForwardIter beg,
           _ForwardIter end,
           _Compare c = _Compare())
{
    _ForwardIter last_pos = end;
    for(_ForwardIter v = beg; v != end; ++v)
    {
        _ForwardIter current_pos = end;
        _ForwardIter b = beg, temp = b;
        for(++temp; temp != last_pos; ++b, ++temp)
        {
            if(c(*temp, *b) > 0)
            {
                swap(*temp, *b);
                current_pos = temp;
            }
        }
        last_pos = current_pos;
        if(last_pos == end)
        { return; }
    }
}

/// 双向冒泡排序
/// 范围:[beg, end)
/// 参数限定:支持前向迭代和后向迭代
template<typename _BothIter,
         typename _Compare = Comparator<decltype(*std::declval<_BothIter>())>>
void bsort(_BothIter beg,
           _BothIter end,
           _Compare c = _Compare())
{
    _BothIter max_pos = end;
    _BothIter min_pos = beg;
    for(_BothIter v = beg; v != end; ++v)
    {
        _BothIter current_pos = end;
        _BothIter b = min_pos, temp = b;
        for(++temp; temp != max_pos; ++b, ++temp)
        {
            if(c(*temp, *b) > 0)
            {
                swap(*temp, *b);
                current_pos = temp;
            }
        }
        if(current_pos == end)
        { return; }
        max_pos = current_pos;
        current_pos = end;
        b = max_pos;
        temp = b;
        for(--temp; b != min_pos; --b, --temp)
        {
            if(c(*b, *temp) > 0)
            {
                swap(*temp, *b);
                current_pos = b;
            }
        }
        ++min_pos;
        if(current_pos == end)
        { return; }
    }
}

如有问题,欢迎指出!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值