#ifndef __STACK_SORT_H__
#define __STACK_SORT_H__
/*
优化说明:
1. 去掉递归
2. 排序栈可以由外部管理, 不需要每次都new delete
3. 支持双向排序
4. 排序携带数据类型
*/
template <class T, class datatype=void*>
struct sort_item
{
T value;
datatype d;
inline bool operator < (const sort_item<T,datatype>& v)
{
return (value < v.value);
}
inline bool operator > (const sort_item<T,datatype>& v)
{
return (value > v.value);
}
inline bool operator ==(const sort_item<T,datatype>& v)
{
return (value == v.value);
}
inline bool operator <=(const sort_item<T,datatype>& v)
{
return (value <= v.value);
}
inline bool operator >=(const sort_item<T,datatype>& v)
{
return (value >= v.value);
}
};
template <class T, class datatype>
inline void swap(sort_item<T, datatype>* a, sort_item<T, datatype>* b)
{
if(a == b)
return;
sort_item<T, datatype> t;
t = *a;
*a = *b;
*b = t;
}
template<class T>
class sort_stack
{
public:
sort_stack(int size)
{
m_size = size;
m_p = new T[m_size];
m_index = -1;
}
~sort_stack()
{
if(m_p)
{
delete m_p;
}
m_p = 0;
m_size = 0;
m_index = 0;
}
inline void pop()
{
if(m_index >= 0)
m_index --;
}
inline T top()
{
if(m_index>=0)
return m_p[m_index];
T t;
memset(&t, 0, sizeof(t));
return t;
}
inline void push(T t)
{
if((m_index+1) < m_size)
{
m_index ++;
m_p[m_index] = t;
}
}
inline int size()
{
if(m_index>=0)
return (m_index+1);
return 0;
}
inline bool empty()
{
return (m_index<0);
}
inline void reset()
{
m_index = -1;
}
private:
T* m_p;
int m_size;
int m_index;
};
template <class T, class datatype>
struct sort_param{
sort_item<T,datatype>* a;
int n;
};
template <class T, class datatype>
inline void stack_sort(sort_item<T,datatype>* a, int n, bool dir=true, sort_stack< sort_param<T,datatype> >* p_stack=0)
{
sort_stack< sort_param<T,datatype> >* ptemp = 0;
if(p_stack)
ptemp = p_stack;
else
ptemp = new sort_stack< sort_param<T,datatype> >(n);
sort_stack< sort_param<T,datatype> >& sp = *ptemp;
sort_param<T,datatype> pm;
if(dir)
{
for(;;){
if( n<=2 ){
if( n==2 && a[1] < a[0])
swap(a, a+1);
if(sp.empty())
break;
pm = sp.top();
sp.pop();
a = pm.a;
n = pm.n;
continue;
}
swap( a, a+(n>>1) );
sort_item<T,datatype> pivot=*a;
sort_item<T,datatype>* l=a+1;
sort_item<T,datatype>* r=a+n-1;
while( l<r )
{
while(l<r && *l<pivot)
l++;
while( r>a && *r>=pivot)
r--;
if( l<r )
swap( l, r );
}
if(*a > *r)
swap( a, r );
pm.a=r+1;
pm.n=n-1-(r-a);
sp.push(pm);
n = r-a;
}
}
else
{
for(;;){
if( n<=2 ){
if(n==2 && a[1] > a[0])
swap(a, a+1);
if(sp.empty())
break;
pm = sp.top();
sp.pop();
a = pm.a;
n = pm.n;
continue;
}
swap( a, a+(n>>1) );
sort_item<T,datatype> pivot=*a;
sort_item<T,datatype>* l=a+1;
sort_item<T,datatype>* r=a+n-1;
while(l < r)
{
while(l<r && *l>pivot)
l++;
while( r>a && *r<=pivot)
r--;
if( l<r )
swap( l, r );
}
if(*a < *r)
swap( a, r );
pm.a=r+1;
pm.n=n-1-(r-a);
sp.push(pm);
n = r-a;
}
}
if(!p_stack)
delete ptemp;
ptemp = 0;
}
template<class T, class datatype=void*>
class sort_buff_helper
{
public:
sort_item<T,datatype>* m_sort_buff;
int m_max;
sort_buff_helper()
{
m_max = 0;
m_sort_buff = 0;
m_sort_stack = 0;
}
void create(int n)
{
if(n<m_max)
return;
if(m_sort_buff)
delete m_sort_buff;
if(m_sort_stack)
delete m_sort_stack;
m_max = n;
m_sort_stack = new sort_stack< sort_param<T,datatype>>(m_max);
m_sort_buff = new sort_item<T,datatype>[m_max];
}
void clear()
{
if(m_sort_buff)
delete m_sort_buff;
if(m_sort_stack)
delete m_sort_stack;
m_max = 0;
m_sort_buff = 0;
m_sort_stack = 0;
}
inline sort_item<T,datatype>& operator [] (int index)
{
return m_sort_buff[index];
}
sort_stack< sort_param<T,datatype>>* get_stack()
{
return m_sort_stack;
}
private:
sort_stack< sort_param<T,datatype>>* m_sort_stack;
};
template <class T, class datatype>
void stack_sort(sort_buff_helper<T,datatype>& buf, int size, bool dir=true)
{
buf.get_stack()->reset();
stack_sort(buf.m_sort_buff, size, dir, buf.get_stack());
}
/*
使用方法Demo:
//模拟排序数据
struct item_tag{
int value;
int grade;
};
//定义排序数据存储
map<unsigned int,item_tag> sort_data;
//...load sort_data;
//创建排序缓存
sort_buff_helper<int,map<unsigned int,item_tag>::iterator> sbuff;
sbuff.create(sort_data.size()+1);
//保存迭代器,回写排序结果时用到
map<unsigned int,item_tag>::iterator i;
int index = 0;
for(i=sort_data.begin(); i!=sort_data.end(); i++)
{
sbuff[index].d = i;
sbuff[index].value = i->second.value;
index ++;
}
bool dir = true;
//排序
stack_sort(sbuff, sort_data.size(), dir);
//回写排序结果
for(int i=0; i<size; i++)
{
sbuff[i].d->second.grade = i;
}
*/
#endif//__STACK_SORT_H__
转载于:https://blog.51cto.com/makala/1177841