关键词搜索

源码搜索 ×
×

快速排序的一种高雅写法

发布2022-06-12浏览965次

详情内容

最近看源码,发现了一段快速排序的代码,挺有意思,一起来看看:

  1. static void
  2. _pqsort(void *a, size_t n, size_t es,
  3. int (*cmp) (const void *, const void *), void *lrange, void *rrange)
  4. {
  5. char *pa, *pb, *pc, *pd, *pl, *pm, *pn;
  6. size_t d, r;
  7. int swaptype, cmp_result;
  8. loop: SWAPINIT(a, es);
  9. if (n < 7) {
  10. for (pm = (char *) a + es; pm < (char *) a + n * es; pm += es)
  11. for (pl = pm; pl > (char *) a && cmp(pl - es, pl) > 0;
  12. pl -= es)
  13. swap(pl, pl - es);
  14. return;
  15. }
  16. pm = (char *) a + (n / 2) * es;
  17. if (n > 7) {
  18. pl = (char *) a;
  19. pn = (char *) a + (n - 1) * es;
  20. if (n > 40) {
  21. d = (n / 8) * es;
  22. pl = med3(pl, pl + d, pl + 2 * d, cmp);
  23. pm = med3(pm - d, pm, pm + d, cmp);
  24. pn = med3(pn - 2 * d, pn - d, pn, cmp);
  25. }
  26. pm = med3(pl, pm, pn, cmp);
  27. }
  28. swap(a, pm);
  29. pa = pb = (char *) a + es;
  30. pc = pd = (char *) a + (n - 1) * es;
  31. for (;;) {
  32. while (pb <= pc && (cmp_result = cmp(pb, a)) <= 0) {
  33. if (cmp_result == 0) {
  34. swap(pa, pb);
  35. pa += es;
  36. }
  37. pb += es;
  38. }
  39. while (pb <= pc && (cmp_result = cmp(pc, a)) >= 0) {
  40. if (cmp_result == 0) {
  41. swap(pc, pd);
  42. pd -= es;
  43. }
  44. pc -= es;
  45. }
  46. if (pb > pc)
  47. break;
  48. swap(pb, pc);
  49. pb += es;
  50. pc -= es;
  51. }
  52. pn = (char *) a + n * es;
  53. r = min(pa - (char *) a, pb - pa);
  54. vecswap(a, pb - r, r);
  55. r = min((size_t)(pd - pc), pn - pd - es);
  56. vecswap(pb, pn - r, r);
  57. if ((r = pb - pa) > es) {
  58. void *_l = a, *_r = ((unsigned char*)a)+r-1;
  59. if (!((lrange < _l && rrange < _l) ||
  60. (lrange > _r && rrange > _r)))
  61. _pqsort(a, r / es, es, cmp, lrange, rrange);
  62. }
  63. if ((r = pd - pc) > es) {
  64. void *_l, *_r;
  65. /* Iterate rather than recurse to save stack space */
  66. a = pn - r;
  67. n = r / es;
  68. _l = a;
  69. _r = ((unsigned char*)a)+r-1;
  70. if (!((lrange < _l && rrange < _l) ||
  71. (lrange > _r && rrange > _r)))
  72. goto loop;
  73. }
  74. /* qsort(pn - r, r / es, es, cmp);*/
  75. }
  76. void
  77. pqsort(void *a, size_t n, size_t es,
  78. int (*cmp) (const void *, const void *), size_t lrange, size_t rrange)
  79. {
  80. _pqsort(a,n,es,cmp,((unsigned char*)a)+(lrange*es),
  81. ((unsigned char*)a)+((rrange+1)*es)-1);
  82. }

快速排序很常见,在笔试面试中也很重要。

相关技术文章

点击QQ咨询
开通会员
返回顶部
×
微信扫码支付
微信扫码支付
确定支付下载
请使用微信描二维码支付
×

提示信息

×

选择支付方式

  • 微信支付
  • 支付宝付款
确定支付下载