废话就不多说了,开始。。。
言前:写这篇博客要主是加深自己对序排算法的懂得和总结实现算法时的一些验经和训教,如果有误错请指出,谢感。
这个是关于算法的维思导图,自己把基于较比的7个算法,写了一个维思导图。维思导图软件应用的是XMind,有免费版感兴趣可以下载。
本文要主分为两个部份,一个是对于算法的懂得另一个是在算法实现过程当中一些验经和训教的总结。
一,关于算法
首先推荐一个子帖http://blog.csdn.net/ctang/article/details/37914 这个是对于算法分析较比好的,在算法实现过程当中要需注意的是快排和归并序排要需应用栈堆或者递归实现。对于快速序排当数据本身有序时会退化到O(N*N)的时间庞杂度中,如果是大数据(我在试测中对于11000以上的有序数据量,就会现出栈堆溢出的常异),因此要需采取非递归,自己应用栈堆较比好。
二、算法实现中的验经和训教
最开始时只是用了一个Isort接口,一共7个算法望希用一个类去实现,在实现过程当中,发明这类实现法方太过于庞杂,因为有的算法还要需助辅函数。
public interface ISort { void SelectSort(); void BubbleSort(); void QuickSort(); void InsertSort(); void ShellSort(); void MergeSort(); void HeapSort(); }
public interface IAlgorithmSort { /// <summary> /// /// </summary> /// <param name="LittleToBig"> 1....to....n or n....to...1 </param> void Sort(bool LittleToBig); }
public void Sort(bool LittleToBig) { if (LittleToBig) SortPositive(); else SortNegitive(); } public abstract void SortPositive(); public abstract void SortNegitive();
全部算法实现后就有一个试测问题,为了便利试测AlgorithmSort类中可以生成随机数据,随机正序数据和随机逆序数据,最开始计划的时候是每次停止序排检测时,都调用一下随机函数,然后序排,践实过程当中发明,每次生成随机数据时间消费太大,因此有增加了几个变量,函数初始化时就生成关相的数据。
_data 是每次序排时要用的数据,_xrData是随机数据,_prData是随机正序数据,_nrData时随机逆序数据,每次序排前_data要需复制关相的数据。
protected const int LENGTH = 10000; private Random _random; protected int [] _data; private int[] _xrData; private int[] _prData; private int[] _nrData;
这个函数的利益是可以通过颜色通知否是符合预期。
AlgorithmSort类的源代码
public interface IAlgorithmSort { /// <summary> /// /// </summary> /// <param name="LittleToBig"> 1....to....n or n....to...1 </param> void Sort(bool LittleToBig); } public abstract class AlgorithmSort : IAlgorithmSort { protected const int LENGTH = 10000; private Random _random; protected int [] _data; private int[] _xrData; private int[] _prData; private int[] _nrData; protected AlgorithmSort() { _random = new Random(); _data = new int[LENGTH]; _xrData = new int[LENGTH]; _prData=new int[LENGTH]; _nrData=new int[LENGTH]; newRandomData(); newRandomPositiveOrderData(); newRandomNegitiveOrderData(); //RandomData(); } private void newRandomData() { for (int i = 0; i < LENGTH; i++) { //_data[i] = _random.Next(-2 * LENGTH, 2 * LENGTH); _xrData[i] = _random.Next(-2 * LENGTH, 2 * LENGTH); } } private void newRandomPositiveOrderData() { int temp = -LENGTH; for (int i = 0; i < LENGTH; i++) { temp = temp + _random.Next(0, 10); _prData[i] = temp; } } private void newRandomNegitiveOrderData() { int temp = LENGTH; for (int i = 0; i < LENGTH; i++) { temp = temp + _random.Next(-10, 0); //_data[i] = temp; _nrData[i] = temp; } } public void RandomData() { //for (int i = 0; i < LENGTH; i++) // _data[i] = _random.Next(-2*LENGTH,2*LENGTH); for (int i = 0; i < LENGTH; i++) { _data[i]=_xrData[i]; } } public void RandomPositiveOrderData() { //int temp = -LENGTH; //for (int i = 0; i < LENGTH; i++) //{ // temp = temp + _random.Next(0, 10); // _data[i] = temp; //} for (int i = 0; i < LENGTH; i++) { _data[i] = _prData[i]; } } public void PositiveOrderData() { for (int i = 0; i < LENGTH; i++) { _data[i] = i+1; } } public void NegitiveOrderData() { for (int i = 0; i < LENGTH; i++) { _data[i] =LENGTH-i; } } public void RandomNegitiveOrderData() { //int temp = LENGTH; //for (int i = 0; i < LENGTH; i++) //{ // temp = temp + _random.Next(-10, 0); // _data[i] = temp; //} for (int i = 0; i < LENGTH; i++) { _data[i] = _nrData[i]; } } public void Sort(bool LittleToBig) { if (LittleToBig) SortPositive(); else SortNegitive(); } public abstract void SortPositive(); public abstract void SortNegitive(); public void Print() { foreach(int ele in _data) { Console.WriteLine(ele); } } protected void swap(ref int a,ref int b) { int c; c = a; a = b; b = c; } public void CheckNOrder() { bool right=true; for (int i = 1; i < LENGTH; i++) { if (_data[i - 1] < _data[i]) { right = false; break; } } ConsoleColor currentForeColor = Console.ForegroundColor; Console.ForegroundColor = ConsoleColor.Yellow; if (right) { Console.ForegroundColor = ConsoleColor.Green; Console.WriteLine("IS Negitive Order"); } else { Console.ForegroundColor = ConsoleColor.Red; Console.WriteLine("Warning Warning Warning Is NOT Negitive Order"); } Console.ForegroundColor = currentForeColor; } public void CheckPOrder() { bool right = true; for (int i = 1; i < LENGTH; i++) { if (_data[i - 1] > _data[i]) { right = false; break; } } ConsoleColor currentForeColor = Console.ForegroundColor; Console.ForegroundColor = ConsoleColor.Yellow; if (right) { Console.ForegroundColor = ConsoleColor.Green; Console.WriteLine("IS Positive Order"); } else { Console.ForegroundColor = ConsoleColor.Red; Console.WriteLine("Warning Warning Warning Is NOT Positive Order"); } Console.ForegroundColor = currentForeColor; } }
三关于性能试测
性能试测应用的是老赵供给的一个简略的性能计数器:CodeTimer ,和自己写的一个Test类,要主可以通过AlgorithmSort 作为一个指针,指向子类,可以试测各种各种详细的序排法方的性能。
函数名命解释:举例Test_N_Random_X ,Test示表是一个试测函数;N示表序排的结果时Negitive即逆序,P代表正序;Random代表应用的数据时随机生成的,X代表随机生成的数据没有次序,P代表随机生成的数据是正序,N则代表是随机生成的数据是逆序,Test_N_Random_X的意思是应用随机无序的数据,实现正序排。
详见代码。
public class Test { private AlgorithmSort _testAlg; public Test(AlgorithmSort alg) { _testAlg = alg; } public void BindAlg(AlgorithmSort alg) { if (alg == null) return; _testAlg = alg; } public void Test_P_Random_X() { _testAlg.RandomData(); _testAlg.SortPositive(); } public void Test_N_Random_X() { _testAlg.RandomData(); _testAlg.SortNegitive(); } public void Test_P_Random_N() { _testAlg.RandomNegitiveOrderData(); _testAlg.SortPositive(); } public void Test_N_Random_P() { _testAlg.RandomPositiveOrderData(); _testAlg.SortNegitive(); } public void Pack_Test(string algName) { string testStr = "试测{0}"; testStr = string.Format(testStr,algName); CodeTimer.Time(testStr+"随机逆序排", 1, Test_N_Random_X); CodeTimer.Time(testStr + "随机正序排", 1, Test_P_Random_X); CodeTimer.Time(testStr + "正序逆排", 1, Test_N_Random_P); CodeTimer.Time(testStr + "逆序正排", 1, Test_P_Random_N); } public void Pack_OutTest(string algName) { string testStr = "试测{0}"; testStr = string.Format(testStr, algName); CodeTimer.Time(testStr + "随机逆序排", 1, Test_N_Random_X); _testAlg.CheckNOrder(); CodeTimer.Time(testStr + "随机正序排", 1, Test_P_Random_X); _testAlg.CheckPOrder(); CodeTimer.Time(testStr + "正序逆排", 1, Test_N_Random_P); _testAlg.CheckNOrder(); CodeTimer.Time(testStr + "逆序正排", 1, Test_P_Random_N); _testAlg.CheckPOrder(); } }
部全代码下载 http://files.cnblogs.com/CaiBaoZi/Sort.rar
文章结束给大家分享下程序员的一些笑话语录: 人脑与电脑的相同点和不同点,人脑会记忆数字,电脑也会记忆数字;人脑会记忆程序,电脑也会记忆程序,但是人脑具有感知能力,这种能力电脑无法模仿,人的记忆会影响到人做任何事情,但是电脑只有程序软件。比尔还表示,人脑与电脑之间最重要的一个差别就是潜意识。对于人脑存储记忆的特别之处,比尔表示,人脑并不大,但是人脑重要的功能是联络,人脑会把同样的记忆存储在不同的地方,因此记忆读取的速度就不相同,而这种速度取决于使用的频率和知识的重要性。人脑的记忆存储能力会随着年龄增长而退化,同时记忆的质量也会随着年龄退化。经典语录网