您的位置:首页 > 其它

快速排序、求旋转数组最小数字

2016-05-25 16:46 471 查看
#include <iostream>
#include <stack>
#include <queue>
#include <algorithm>

using namespace std;

// 快速排序1
void quickSort( int a[], int l, int r )
{
if( l >= r )
{
return;
}

int i = l;
int j = r;

int mid = ( l + r ) / 2;
int tmp = a[mid];
a[mid] = a[l];
a[l] = tmp;

int value = a[l];

while( i < j )
{

while( i < j && a[j] >= value ) j--;

a[i] = a[j];

while( i < j && a[i] <= value ) i++;

a[j] = a[i];

}

a[i] = value;

quickSort( a, l, i - 1 );
quickSort( a, i + 1, r );

return;

}

// 快速排序2,容易理解的快排
void quickSort1( int a[], int start, int end )
{
if( start >= end )
{
return;
}

int mid = ( start + end ) / 2;
int tmp = a[mid];
a[mid] = a[end];
a[end] = tmp;

int idx = start - 1;

for( int i = start; i < end; i++ )
{
if( a[i] < a[end] )   // a[end]作为pivot
{
idx++;

if( idx != i )
{
int tmp = a[idx];
a[idx] = a[i];
a[i] = tmp;
}
}
}

idx++;
tmp = a[idx];
a[idx] = a[end];
a[end] = tmp;

quickSort1( a, start, idx - 1 );
quickSort1( a, idx + 1, end );

return;
}

void print( int a[], int len )
{
for( int i = 0; i < len; i++ )
{
cout << a[i] << ' ';
}

cout << endl;

return;
}

// 求旋转数组的最小数字 递归实现
int midRotatedArray( int a[], int start, int end )
{
int min = -1;

if( NULL == a )
{
min = -1;
return min;
}

if( start >= end )
{
min = a[start];
return min;
}

int mid = ( start + end ) / 2;

//if( a[mid] <= a[ ( mid + 1 ) %
int right = mid + 1 > end ? start : mid + 1;
int left = mid - 1 < start ? end: mid - 1;

if( a[mid] <= a[right] && a[mid] <= a[left] )
{
if( !( a[mid] == a[right] && a[mid] == a[left] ) ) // for { 2 3 3 3 1 }
{
min = a[mid];
//cout << start << ' ' << mid << ' ' << end << endl;
return min;
}

}

int minLeft = midRotatedArray( a, start, mid - 1 );
int minRight = midRotatedArray( a, mid + 1, end );

return minLeft > minRight ? minRight : minLeft;

}

// 求旋转数组的最小数字 非递归实现
int midRotatedArray_noRecur( int a[], int start, int end )
{
int min = -1;

if( NULL == a )
{
min = -1;
return min;
}

if( start >= end )
{
min = a[start];
return min;
}

int mid = ( start + end ) / 2;

while( a[start] >= a[end] )
{
mid = ( start + end ) / 2;

int right = mid + 1 > end ? start : mid + 1;
int left = mid - 1 < start ? end : mid - 1;

if( a[mid] <= a[right] && a[mid] <= a[left] )
{
if( !( a[mid] == a[right] && a[mid] == a[left] ) )
{
min = a[mid];
//cout << start << ' ' << mid << ' ' << end << endl;
return min;
}

}

if( a[start] == a[mid] && a[mid] == a[end] ) // 顺序查找, for : { 1 0 1 1 1 } and  { 1 1 1 0 1 }
{
min = a[start];

for( int i = start + 1; i <= end; i++ )
{
if( min > a[i] )
{
min = a[i];
}
}

return min;
}

if( start != mid && a[start] >= a[mid] )
{
end = mid - 1;
}
else
{
start = mid + 1;
}

}

min = a[start];
return min;
}

// 总结: 先写测试用例,否则很多考虑不周

int main()
{
int ret = 0;
int data = -2;
data = data << 2;
cout << data << endl;

data = -2;
data = data >> 2;
cout << data << endl;
// 针对求旋转数组的最小数字的测试用例
int b0[] = { 3, 4, 5, 6, 1 };
int b1[] = { 2, 2, 3, 0, 1 };
int b2[] = { 1, 2, 3, 4, 5 };
int b3[] = { 2, 2, 2, 2, 2 };
int b4[] = { 1, 1, 1, 0, 1 };
int b5[] = { 1, 0, 1, 1, 1 };
int b6[] = { 2, 1 };
int b7[] = { 3 };
int *b8 = NULL;

cout << midRotatedArray( b7, 0, 0 ) << endl;
cout << midRotatedArray_noRecur( b7, 0, 0 ) << endl;

int a1[] = { 1, 2, 3, 4, 5 };
int a2[] = { 5, 4, 3, 2, 1 };
int a3[] = { 5, 7, 1, 3, 6 };
int a4[] = { 5, 4, 4, 4, 1 };
int a5[] = { 4, 4, 4, 4, 4 };

quickSort1( a1, 0, 4 );
quickSort1( a2, 0, 4 );
quickSort1( a3, 0, 4 );
quickSort1( a4, 0, 4 );
quickSort1( a5, 0, 4 );

print( a1, 5 );
print( a2, 5 );
print( a3, 5 );
print( a4, 5 );
print( a5, 5 );

return ret;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息