第二章 算法入门
用C++实现本章节及习题的一些算法
/************************************************************************/
/*插入排序;
/************************************************************************/
template <class T>
void InsertionSort(T* _array,int n)
{
if (n > 1)
{
int j;
for (int i = 1; i < n; ++i)
{
T key = _array[i];
j = i - 1;
while(j >= 0 && key < _array[j])
{
_array[j + 1] = _array[j];
j = j - 1;
}
_array[j +1] = key;
}
}
}
/************************************************************************/
/*归并排序;
/************************************************************************/
template <class T>
void Merge(T* _array,int p, int q, int r)
{
const int n1 = q - p + 1;
const int n2 = r - q ;
T *_array1 = NULL,*_array2 = NULL;
try
{
_array1 = new T[n1];
_array2 = new T[n2];
}
catch (...)
{
if (_array1 != NULL)
{
delete [] _array1;
_array1 = NULL;
}
if (_array2 != NULL)
{
delete [] _array2;
_array2 = NULL;
}
}
for (int i = 0; i < n1; ++i)
{
_array1[i] = _array[p + i];
}
for (int i = 0; i < n2; ++i)
{
_array2[i] = _array[q + i + 1];
}
int k,i,j;
i = 0;
j = 0;
for ( k = p; k <= r; ++k)
{
if (_array1[i] < _array2[j])
{
_array[k] = _array1[i];
++i;
if (i == n1)
{
break;
}
}
else
{
_array[k] = _array2[j];
++j;
if (j == n2)
{
break;
}
}
}
if (k < r)
{
k++;
if (i < n1)
{
for (int h = i; h < n1; ++h)
{
_array[k] = _array1[h];
++k;
}
}
else
{
for (int h = j; h < n2; ++h)
{
_array[k] = _array2[h];
++k;
}
}
}
if (_array1 != NULL)
{
delete [] _array1;
_array1 = NULL;
}
if (_array2 != NULL)
{
delete [] _array2;
_array2 = NULL;
}
}
template <class T>
void _MergeSort(T* _array,int p,int r)
{
if (p < r)
{
int q = (p + r)/2;
_MergeSort(_array,p,q);
_MergeSort(_array,q + 1,r);
Merge(_array,p,q,r);
}
}
template <class T>
void MergeSort(T* _array,int n)
{
_MergeSort(_array,0,n - 1);
}
/************************************************************************/
/*采用归并排序与插入排序混合方式,当n <k时采用插入排序;
/************************************************************************/
template <class T>
void _MergeSort_Insertion(T* _array,int p,int r,int k = 5)
{
if ((r - p + 1) < k)
{
InsertionSort(_array + p, r - p + 1);
}
else
{
int q = (p + r)/2;
_MergeSort_Insertion(_array,p,q,k);
_MergeSort_Insertion(_array,q + 1,r,k);
Merge(_array,p,q,r);
}
}
template <class T>
void MergeSort_Insertion(T* _array,int n)
{
_MergeSort_Insertion(_array,0,n - 1,log((float)n)/log((float)2));
}
/************************************************************************/
/*选择排序;
/************************************************************************/
template <class T>
void SelectSort(T* a,int n)
{
int min_index;
T tem;
for (int i = 0; i < n - 1; ++i)
{
min_index = i;
for (int j = i + 1; j < n; ++j)
{
if (a[min_index] > a[j])
{
min_index = j;
}
}
tem = a[i];
a[i] = a[min_index];
a[min_index] = tem;
}
}
/************************************************************************/
/*冒泡排序;
/************************************************************************/
template <class T>
void BubbleSort(T* a,int n)
{
T temp;
for (int i = 0; i < n - 1; ++i)
{
for (int j = n - 1; j > i; --j)
{
if (a[j] < a[j-1])
{
temp = a[j];
a[j] = a[j - 1];
a[j - 1] = temp;
}
}
}
}
/************************************************************************/
/*霍纳规则计算多项式的值;
/************************************************************************/
int Horner(int* a,int n,int x)
{
int res = 0;
int i = n - 1;
while(i >= 0)
{
res = a[i] + x*res;
i--;
}
return res;
}
/************************************************************************/
/* 计算逆序对数目;
/************************************************************************/
template <class T>
int InversionCount(T* _array,int p, int q, int r)
{
const int n1 = q - p + 1;
const int n2 = r - q ;
int res = 0;
T *_array1 = NULL,*_array2 = NULL;
try
{
_array1 = new T[n1];
_array2 = new T[n2];
}
catch (...)
{
if (_array1 != NULL)
{
delete [] _array1;
_array1 = NULL;
}
if (_array2 != NULL)
{
delete [] _array2;
_array2 = NULL;
}
}
for (int i = 0; i < n1; ++i)
{
_array1[i] = _array[p + i];
}
for (int i = 0; i < n2; ++i)
{
_array2[i] = _array[q + i + 1];
}
int k,i,j;
i = 0;
j = 0;
for ( k = p; k <= r; ++k)
{
if (_array1[i] < _array2[j])
{
_array[k] = _array1[i];
++i;
if (i == n1)
{
break;
}
}
else
{
_array[k] = _array2[j];
++j;
res += q - p - i + 1;
if (j == n2)
{
break;
}
}
}
if (k < r)
{
k++;
if (i < n1)
{
for (int h = i; h < n1; ++h)
{
_array[k] = _array1[h];
++k;
}
}
else
{
for (int h = j; h < n2; ++h)
{
_array[k] = _array2[h];
++k;
}
}
}
if (_array1 != NULL)
{
delete [] _array1;
_array1 = NULL;
}
if (_array2 != NULL)
{
delete [] _array2;
_array2 = NULL;
}
return res;
}
template <class T>
int _Inversion(T* _array,int p,int r)
{
int res = 0;
if (p < r)
{
int q = (p + r)/2;
res +=_Inversion(_array,p,q);
res +=_Inversion(_array,q + 1,r);
res += InversionCount(_array,p,q,r);
}
return res;
}
template <class T>
int Inversion(T* _array,int n)
{
int res = 0;
res = _Inversion(_array,0,n - 1);
return res;
}
/************************************************************************/
/*线性搜索;
/************************************************************************/
template <class T>
int Search(T* _array,int n, T val)
{
for (int i = 0; i < n; ++i)
{
if (_array[i] == val)
{
return ++i;
}
}
return NIL;
}