/*
* File: main.cpp
* Author: virtualdemon
*
* Created on December 31, 2009, 7:28 PM
*/
#include <vector>
#include <fstream>
#include <iterator>
/*
*
*/
using namespace std;
vector<int> v;
int size_threshold;
inline void swap( int x, int y )
{
v[x]+=v[y];
v[y]=v[x]-v[y];
v[x]-=v[y];
}
void siftdown( int s, int e )
{
int w=2*s+1;
while( w < e )
{
if( w+1 < e && v[w+1] > v[w] )
++w;
if( v[w] <= v[s] )
return;
swap( s, w );
s=w;
w=2*s+1;
}
}
void downheap( int s, int e )
{int r=2*s+1;
while( r < e )
{
if( r+1 < e && v[r] < v[r+1] ) ++r;
if( v[r] <= v[s] ) return; //has heap structure
swap( r, s );
s=r;
r=2*s+1;
}
}
void HeapSort( int s, int e )
{
for( int w=e/2-1; w > s; --w )
downheap( w, e ); //creat a heap from the arrat v
downheap( s, e );
for( e=e-1; e > s; --e )
{
swap( s, e );
downheap( s, e );
}
}
inline int medianof3( int left, int middle, int right )
{
if( v[left] > v[middle] )
swap( left, middle );
if( v[left] > v[right] )
swap( left, right );
if( v[middle] > v[right] )
swap( middle, right );
swap( middle, right-1 );
return v[right-1];
}
int Partition( int left, int right, int pValue )
{
int leftPtr=left, rightPtr=right;
while( true )
{
while( v[++leftPtr] < pValue );
while( v[--rightPtr] > pValue );
if( leftPtr >= rightPtr )
break;
swap( leftPtr, rightPtr );
}
swap( left, right-1 );
return leftPtr;
}
void Introsort_Loop( int left, int right, int depth_limit )
{
while( right-left > size_threshold )
{
if( !depth_limit )
{
HeapSort( left, right );
return;
}
--depth_limit;
int p=Partition( left, right, medianof3( left, left+(right-left)/2-1, right-1 ) );
Introsort_Loop( p, right, depth_limit );
right=p;
}
}
void Insertion_Sort( int left, int right )
{int key, j;
for( left+=1; left < right; ++left )
{
key=v[left];
for( j=left-1; j >=0 && v[j] > key; --j )
v[j+1]=v[j];
v[j+1]=key;
}
}
void Bubble_Sort( int left, int right )
{
int
do
{
ok=false;
--right;
for( i=left; i < right; ++i )
if( v[i] > v[i+1] )
ok=true, swap( v[i], v[i+1] );
--right;
}while( ok );
}
inline int Log2( int n)
{
int pos = 0;
if (n >= 1<<16) { n >>= 16; pos += 16; }
if (n >= 1<< 8) { n >>= 8; pos += 8; }
if (n >= 1<< 4) { n >>= 4; pos += 4; }
if (n >= 1<< 2) { n >>= 2; pos += 2; }
if (n >= 1<< 1) { pos += 1; }
return ((n == 0) ? (-1) : pos);
}
int main()
{int n;
ifstream in("algsort.in");
in>>n;
copy( istream_iterator<int>(in), istream_iterator<int>(), back_inserter(v) );
size_threshold=16;
/*Introsort start here*/
Introsort_Loop( 0, n, 2*Log2(n) );
Bubble_Sort( 0, n );
/*end here*/
ofstream out("algsort.out");
copy( v.begin(), v.end(), ostream_iterator<int>(out, " " ) );
return 0;
}