【快速排序】快速排序与数学归纳法

      public delegate bool CompareDelegate(HPoint2d point0, HPoint2d point1);

      public void QuikSort(List<HPoint2d> lstPoint, int indexS, int indexE, CompareDelegate 
         compare)
      {
         if (indexE <= indexS)
            return;

         int indexP = Partition(lstPoint, indexS, indexE, compare);
         QuikSort(lstPoint, indexS, indexP - 1, compare);
         QuikSort(lstPoint, indexP + 1, indexE, compare);
      }

      public int Partition(List<HPoint2d> lstPoint, int indexS, int indexE, CompareDelegate 
         compare)
      {
         HPoint2d ptBase = lstPoint[indexE];
         int i = indexS - 1;
         for(int j = indexS; j < indexE; j++)
         {
            if(compare(lstPoint[j], ptBase))
            {
               i++;
               var ptTemp = lstPoint[i];
               lstPoint[i] = lstPoint[j];
               lstPoint[j] = ptTemp;
            }
         }

         var ptTemp2 = lstPoint[i + 1];
         lstPoint[i + 1] = lstPoint[indexE];
         lstPoint[indexE] = ptTemp2;

         return i + 1;
      }

(1)对于一个序列,首先将各元素与最后一个元素进行比较,并将较小的元素放到其左边,较大元素放到其右边;

(2)得到两个子序列,对每个子序列按上述方法处理,递归处理;

(3)即得到原位置已排序号的序列。

关键位置在Partition方法,该方法运用了归纳法,

1)初始条件:int i = indexS - 1;int j = indexS;

i及其前的所有元素都小于最后一个元素ptBase;i与j之间([i,j))的所有元素都大于ptBase

2)若j<ptBase,说明比ptBase小的元素增加1,即i++,并将i与j元素互换;----情况1

若j>ptBase,不作处理;----情况2

然后j++进行下一次判断。

注意i与j元素互换的一步是为了处理当出现情况2后再次出现情况1时,比ptBase小的元素应该+1(i++),为了保证处理后仍然满足i及其前的所有元素都小于最后一个元素ptBase;i与j之间([i,j))的所有元素都大于ptBase需将i位置元素(大于ptBase)与j位置元素(小于ptBase)互换。

3)经过第二步处理后,依然满足i及其前的所有元素都小于最后一个元素ptBase;i与j之间([i,j))的所有元素都大于ptBase这一条件;

4)循环第二步直到j==indexEnd-1;每次处理后都满足上述红色字体所注条件;

结束循环时,对于该序列,i及其前的所有元素都小于最后一个元素ptBase;i与j之间([i,j))的所有元素都大于ptBase,此时只需要将i+1位置元素(大于ptBase)与ptBase位置互换后就满足该序列ptBase(i+1位置)之前的所有元素小于等于ptBase,之后的所有元素大于ptBase,

这样一个序列已经划分为两个子序列,对每个子序列按上述递归得到在原位置排序好的序列。

如果将判断依据作为参数传入快排方法,就会灵活很多。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值