代码有部分可能有重复定义,去除/**/
//头文件01.h
#pragma once
#ifndef H01
#define H01
#include<iostream>
using std::cout;
using std::cin;
const int M=10;
template <class T>
bool less(T *p, int a, int b)
{
if (p[a] <p[b]) return 1;
else return 0;
}
template <class T>
bool less(T a, T b)
{
if (a<b) return 1;
else return 0;
}
template <class T>
void show(T *a, int p)
{
for (int i = 0; i <= p; i++) //问题所在,sizeof(a)是元素长度不是数组长度?
cout << a[i] << " ";
cout << std::endl;
}
template <class T>
void show(T *a, int k,int p)
{
for (int i = k; i <= p; i++) //问题所在,sizeof(a)是元素长度不是数组长度?
cout << a[i] << " ";
cout << std::endl;
}
template <class T>
void change(T *a, int c, int b)
{
T t;
t = a[c];
a[c] = a[b];
a[b] = t;
}
template <class T>
void xuanze(T *p, int a, int b)
{
int i = a;
for (; i <= b; i++)
{
int min = i;
for (int j = i + 1; j <= b; j++)
if (p[j] < p[min])
min = j;
change(p, min, i);
}
}
template <class T>
void charu(T *p, int a, int b)
{
for (int i = 1; i <= b; i++)
for (int j = i; j > 0 && less(p, j, j - 1); j--)
change(p, j, j - 1);
}
template <class T>
void merge(T *p, int lo, int mid, int hi)
{
if (hi <= lo) return;
int i = lo, j = mid + 1;
T temp[100];
for (int h = lo; h <= hi; h++)
temp[h] = p[h];
for (int k = lo; k <= hi; k++)
{
if (i > mid) p[k] = temp[j++];
else if (j > hi) p[k] = temp[i++];
else if (less(temp[i], temp[j])) p[k] = temp[i++];
else p[k] = temp[j++];
}
//delete[] temp;
}
int min(int a, int b)
{
return (a > b )? b: a;
}
#endif
//希尔排序
#include "stdafx.h"/*
#include"01.h"
#include<iostream>
using std::cout;
using std::cin;
*/
/*
int xier() //希尔排序
{
int a[M];
int i;
for (i = 0; i < M; i++)
a[i] = rand() % 200 + 100;
show(a, M);
int h = 1;
int n = M;
while (h < n / 3)
h = 3 * h + 1;
int j, k;
while (h >= 1) //步距最小为1
{
for (j = h; j < M; j++) //步距h,从第h个开始比,比完往后以为开始比
for (k = j; k >= h && (less(a, k, k - h)); k -= h) //以k为基准,比较k与每k-h距离的元素的大小,可以长距离地移动元素,节省时间
{
change(a, k, k - h); //01.h建了一些基本函数,自底而上的并归.cpp和希尔排序.cpp都包含了头文件;结果给我报错,可是
show(a, M);
}
h /= 3;
}
show(a, M);
return 1;
}
*/
//自上而下的归并
#include "stdafx.h"/*
#include"01.h"
#include<iostream>
using std::cout;
using std::cin;
template <class T>
void sort(T *p, int lo, int hi)
{
if (hi <= lo) return;
int mid = lo + (hi - lo) / 2;
sort(p, lo, mid);
sort(p, mid + 1, hi);
merge(p, lo, mid, hi);
}
//自上而下的并归
int binggui()
{
int a[15] = { 23, 59, 89, 48, 69, 89, 99, 899, 1, 2, 3, 4, 55, 68, 19 };
//for (int i = 0; i < 15; i++)
// a[i] = rand() % 300 + 100;
show(a, 14);
//merge(a, 0,7,14);
sort(a, 0, 14);
show(a, 14);
return 1;
}*/
//自底而上的并归
#include "stdafx.h"/*
#include"01.h"
#include<iostream>
#include<ctime>
using std::cout;
using std::cin;
int binggui02() //自底而上的并归
{
srand(time(0));
int a[M];// = { 23, 59, 89, 48, 69, 89, 99, 899, 1, 2, 3, 4, 55, 68, 19 };
for (int i = 0; i < M; i++)
a[i] = rand() % 300 + 100;
show(a, 14);
int i ;
int lo = 0, hi = M - 1, o = 1;
for (i = 1; i < M; i *= 2) //循环时循环因子以整个并归的大小为准,而不是中值,前者容易写出结束条件
for (lo=0; lo < M - i; lo = lo + i + i)
merge(a, lo, lo + i-1, min(lo + i + i - 1, hi)); //mid= lo + i-1,此处需要减1,设只有两个数,不减一,mid=1,调用merge时的mid=1+1=2;排序有问题
show(a, 14);
return 1;
}*/
//快速排序和三向切分
#include "stdafx.h"
#include "stdafx.h"
#include"01.h"
#include<iostream>
#include<ctime>
using std::cout;
using std::cin;
using std::endl;
template <class T>
int find(T *p, int lo, int hi) //找出节点
{
T v = p[lo];
int i = lo, j = hi + 1;
while (1)
{
while (less(p[++i], v)) if (i == hi) break;
while (less(v,p[--j])) if (j == lo) break;
if (i >= j) break;
change(p, i, j);
}
change(p, lo, j);
show(p, M - 1);
return j;
}
template <class T> //递归分类
void sort0(T *p, int lo, int hi)
{
if (lo >= hi) return;
int a = find(p, lo, hi);
sort0(p, lo, a-1);
sort0(p, a+1, hi);
}
int kuaisuchazhao() //找出一个节点,以第一个元素为基准,从两端开始比较,遇到左边比a[0]大和右边比a[0]大时,交换位置,再把a[0]放在相遇位置的合适一遍,形成左边比其小,右边比其大
{
srand(time(0));
int a[M];
for (int i = 0; i < M; i++)
a[i] = rand() % 100;
show(a, M - 1);
sort0(a, 0, M - 1);
show(a,M - 1);
cin.get();
return 0;
}
template <class T>
void sort(T *p, int lo, int hi)
{
if (hi <= lo) return;
int n=lo, m=hi, i = lo + 1;
while (i <= m)
{
if (p[i] < p[lo]) change(p, i++, n++); //n始终指着第一个元素,也是居中的首元素,故在下一次递归时需要“n-1”,m同理。
else if (p[i]>p[lo]) change(p, i, m--);
else i++;
}
sort(p, lo, n - 1);
sort(p, m+1, hi);
}
int sanxiangqiefen() //三向切分法,把首元素设为中间值,开头指针n,结束指针m,通过i从左往右,碰到大的往后,小的往前。
{
srand(time(0));
int a[M];
for (int i = 0; i < M; i++)
a[i] = rand() % 100;
show(a, M - 1);
sort(a, 0, M - 1);
show(a, M - 1);
cin.get();
return 0;
}