1、归并排序:
#ifndef SORT_H
#define SORT_H
#include "Object.h"
namespace XiebsLib
{
class Sort : public Object
{
private:
Sort();
Sort(const Sort&);
Sort& operator=(const Sort&);
template <typename T>
static void Swap(T& a, T& b)
{
T c = a;
a = b;
b = c;
}
template<typename T>
static void Merge(T src[], T helper[], int begin, int mid, int end, bool min2max = true)
{
int i = begin;
int j = mid + 1;
int k = begin;
while(i <= mid && j <= end)
{
if(min2max ? (src[i] < src[j]) : (src[i] > src[j]))
{
helper[k++] = src[i++];
}
else
{
helper[k++] = src[j++];
}
}
while(i <= mid)
{
helper[k++] = src[i++];
}
while(j <= end)
{
helper[k++] = src[j++];
}
for(int i = begin; i <= end; i++)
{
src[i] = helper[i];
}
}
template<typename T>
static void Merge(T src[], T helper[], int begin, int end, bool min2max = true)
{
if(begin == end)
{
return;
}
else
{
int mid = (begin + end) / 2;
Merge(src, helper, begin, mid, min2max);
Merge(src, helper, mid+1, end, min2max);
Merge(src, helper, begin, mid, end, min2max);
}
}
public:
template<typename T>
static void Select(T array[], int len, bool min2max = true)
{
for(int i = 0; i < len; i++)
{
int min = i;
for(int j = i + 1; j < len; j++)
{
if(min2max ? (array[min] > array[j]) : (array[i] < array[j]))
{
min = j;
}
}
if(min != i)
{
Swap(array[i],array[min]);
}
}
}
template < typename T >
static void insert(T array[], int len, bool min2max = true)
{
for(int i = 1; i < len; i++)
{
int k = i;
T e = array[i];
for(int j = i-1; (j >= 0) && (min2max ? array[j] > e : array[j] < e); j--)
{
array[j+1] = array[j]; //满足条件的后移一位
k = j;
}
if(i != k)
{
array[k] = e;
}
}
}
template < typename T >
static void Bubble(T array[], int len, bool min2max = true)
{
bool exchange = true;
for(int i = 0; i < len && exchange; i++)
{
exchange = false;
for(int j = len-1; j > i; j--)
{
if(min2max ? (array[j-1] > array[j]) : (array[j-1] < array[j]))
{
Swap(array[j-1], array[j]);
exchange = true;
}
}
}
}
template < typename T >
static void Shell(T array[], int len, bool min2max = true)
{
int d = len;
do
{
d = d / 3 + 1; // 之所以这样写是因为经过数学推导,这样的效率是最高的。也可以写成 d--;
for(int i = d; i < len; i += d)
{
int k = i;
T e = array[i];
for(int j = i-d; (j >= 0) && (min2max ? array[j] > e : array[j] < e); j -= d)
{
array[j+d] = array[j];
k = j;
}
if(i != k)
{
array[k] = e;
}
}
}
while(d > 1);
}
// template < typename T >
// static void Shell_Bubble(T array[], int len, bool min2max = true)
// {
// int d = len;
// do
// {
// d = d / 3 + 1; // 之所以这样写是因为经过数学推导,这样的效率是最高的。也可以写成 d--;
// bool exchange = true;
// for(int i = 0; i < len && exchange; i += d)
// {
// exchange = false;
// for(int j = len-1; j > i; j-=d)
// {
// if(min2max ? (array[j-d] > array[j]) : (array[j-d] < array[j]))
// {
// Swap(array[j-d], array[j]);
// exchange = true;
// }
// }
// }
// }
// while(d > 1);
// }
template<typename T>
static void Merge(T array[], int len, bool min2max = true)
{
T* helper = new T[len];
if(helper != nullptr)
{
Merge(array, helper, 0, len - 1, min2max);
}
delete []helper;
}
};
}
#endif // SORT_H
#include <iostream>
#include "Sort.h"
using namespace std;
using namespace XiebsLib;
int main()
{
int array[] = {9, 3, 2, 4, 1, 5, 7, 6, 9, 8};
Sort::Merge(array, 10, false);
for(int i = 0; i < 10; i++)
{
cout << array[i] << endl;
}
}
2、快速排序
#ifndef SORT_H
#define SORT_H
#include "Object.h"
namespace XiebsLib
{
class Sort : public Object
{
private:
Sort();
Sort(const Sort&);
Sort& operator=(const Sort&);
template <typename T>
static void Swap(T& a, T& b)
{
T c = a;
a = b;
b = c;
}
template<typename T>
static void Merge(T src[], T helper[], int begin, int mid, int end, bool min2max = true)
{
int i = begin;
int j = mid + 1;
int k = begin;
while(i <= mid && j <= end)
{
if(min2max ? (src[i] < src[j]) : (src[i] > src[j]))
{
helper[k++] = src[i++];
}
else
{
helper[k++] = src[j++];
}
}
while(i <= mid)
{
helper[k++] = src[i++];
}
while(j <= end)
{
helper[k++] = src[j++];
}
for(int i = begin; i <= end; i++)
{
src[i] = helper[i];
}
}
template<typename T>
static void Merge(T src[], T helper[], int begin, int end, bool min2max = true)
{
if(begin == end)
{
return;
}
else
{
int mid = (begin + end) / 2;
Merge(src, helper, begin, mid, min2max);
Merge(src, helper, mid+1, end, min2max);
Merge(src, helper, begin, mid, end, min2max);
}
}
template<typename T>
static int Partition(T array[], int begin, int end, bool min2max = true)
{
T pv = array[begin];
while(begin < end)
{
while(begin < end && (min2max ? (array[end] > pv) : (array[end] < pv)))
{
end--;
}
Swap(array[begin], array[end]);
while(begin < end && (min2max ? (array[begin] <= pv) : (array[begin] >= pv)))
{
begin++;
}
Swap(array[begin], array[end]);
}
array[begin] = pv;
return begin;
}
template<typename T>
static void Quick(T array[], int begin, int end, bool min2max = true)
{
if(begin < end)
{
int pivot = Partition(array, begin, end, min2max);
Quick(array, begin, pivot-1, min2max);
Quick(array, pivot+1, end, min2max);
}
}
public:
template<typename T>
static void Select(T array[], int len, bool min2max = true)
{
for(int i = 0; i < len; i++)
{
int min = i;
for(int j = i + 1; j < len; j++)
{
if(min2max ? (array[min] > array[j]) : (array[i] < array[j]))
{
min = j;
}
}
if(min != i)
{
Swap(array[i],array[min]);
}
}
}
template < typename T >
static void insert(T array[], int len, bool min2max = true)
{
for(int i = 1; i < len; i++)
{
int k = i;
T e = array[i];
for(int j = i-1; (j >= 0) && (min2max ? array[j] > e : array[j] < e); j--)
{
array[j+1] = array[j]; //满足条件的后移一位
k = j;
}
if(i != k)
{
array[k] = e;
}
}
}
template < typename T >
static void Bubble(T array[], int len, bool min2max = true)
{
bool exchange = true;
for(int i = 0; i < len && exchange; i++)
{
exchange = false;
for(int j = len-1; j > i; j--)
{
if(min2max ? (array[j-1] > array[j]) : (array[j-1] < array[j]))
{
Swap(array[j-1], array[j]);
exchange = true;
}
}
}
}
template < typename T >
static void Shell(T array[], int len, bool min2max = true)
{
int d = len;
do
{
d = d / 3 + 1; // 之所以这样写是因为经过数学推导,这样的效率是最高的。也可以写成 d--;
for(int i = d; i < len; i += d)
{
int k = i;
T e = array[i];
for(int j = i-d; (j >= 0) && (min2max ? array[j] > e : array[j] < e); j -= d)
{
array[j+d] = array[j];
k = j;
}
if(i != k)
{
array[k] = e;
}
}
}
while(d > 1);
}
// template < typename T >
// static void Shell_Bubble(T array[], int len, bool min2max = true)
// {
// int d = len;
// do
// {
// d = d / 3 + 1; // 之所以这样写是因为经过数学推导,这样的效率是最高的。也可以写成 d--;
// bool exchange = true;
// for(int i = 0; i < len && exchange; i += d)
// {
// exchange = false;
// for(int j = len-1; j > i; j-=d)
// {
// if(min2max ? (array[j-d] > array[j]) : (array[j-d] < array[j]))
// {
// Swap(array[j-d], array[j]);
// exchange = true;
// }
// }
// }
// }
// while(d > 1);
// }
template<typename T>
static void Merge(T array[], int len, bool min2max = true)
{
T* helper = new T[len];
if(helper != nullptr)
{
Merge(array, helper, 0, len - 1, min2max);
}
delete []helper;
}
template<typename T>
static void Quick(T array[], int len, bool min2max = true)
{
Quick(array, 0, len - 1, min2max);
}
};
}
#endif // SORT_H
#include <iostream>
#include "Sort.h"
using namespace std;
using namespace XiebsLib;
int main()
{
int array[] = {9, 3, 2, 4, 1, 5, 7, 6, 9, 8};
Sort::Quick(array, 10, false);
for(int i = 0; i < 10; i++)
{
cout << array[i] << endl;
}
}
- 小结
1、归并排序需要额外的辅助空间才能完成,空间复杂度为 O(n);
2、归并排序的时间复杂度为 O(n * logn),是一种稳定的排序法;
3、快速排序通过对递归的方式对排序问题进行划分;
4、快速排序的时间复杂度为 O(n * logn),是一种不稳定的排序法。