当前位置: 首页 > news >正文

不情愿算法学概论

本文翻译自论文 Pessimisal Algorithms and Simplexity Analysis,这是一篇近四十年前发表的恶搞性质的文章。原文标题显然是 neta 自 Optimal Algorithms(最佳算法)和 Complexity Analysis(时间复杂度分析)。有兴趣的读者可以看看原文。

引入

考虑以下的问题:现在有 \(n\) 个整数 \(A_1,A_2,...,A_n\),我们希望在其中找到一个整数 \(X\)。但这一次不同,我们一点也不着急找到这个 \(X\),甚至,现在出于一些需要,我们希望找到 \(X\) 的速度越慢越好。

我们或许可以考虑使用朴素算法,也就是从 \(A_1\) 遍历到 \(A_n\) 并判断 \(X\) 是否与 \(A_i\) 相等。然而,当 \(X = A_1\) 时,这样的算法只一次循环就会终止;也就是说,朴素的线性查找算法,最佳时间复杂度居然快达 \(\text{O}(1)\)。那么,我们应该如何做得更好,或者说在这个语境下,更慢呢?

我们当然可以在对元素做比较时添加一个没有任何用处的循环,但这样简单的解法是不可接受的。毕竟在这种逻辑下,即使是只学了循环结构的初学者都能看出来这算法纯纯是在故意浪费时间。因此,我们必须寻找一种确实可以缓慢但坚定地向着我们的目标推进的算法,只是这个算法可能有非常小的热情,甚至非常明显地讨厌向这个目标前进。

幸运的是,当 \(\left\{A_{n}\right\}\) 已经从小到大排好序时,我们设法找到了一个这样的“不情愿”算法(也就是不情愿达到目标的算法)。考虑以下 C++ 代码:

// 当存在一个 l <= k <= r 使得 A[k] == X 时,返回这个 k;否则返回 -1.
int research(int X, int *A, int l, int r)
{if (l > r) return -1;if (l == r) return X == A[l] ? i : -1;int mid = (l + r) / 2;if (X <= A[mid]) {int k = research(X, A, mid + 1, r);return k == -1 ? research(X, A, l, mid) : k;} else {int k = research(X, A, l, mid);return k == -1 ? research(X, A, mid + 1, r) : k;}
}

若设此算法的时间复杂度为 \(T(n)\),则可列出方程

\(T(n)=2T(n / 2)+1\),加之边界条件 \(T(1)=1\),可以解得

\(T(n) = O(n)\)

这代表着我们算法相对于之前的朴素算法一个巨达 \(n\) 倍的改退。从宏观上来看,这份代码对找到答案的不热情并不是那么容易看出来,毕竟它对于 X == A[i] 的判断有着平均每次 \(\text{O}(1)\) 的复杂度,不进行重复的判断,并且它在找到一个答案以后就会立刻终止。不管你信不信,很少有查找算法能够达到如此之高的低效程度。

一般化

前面的 research 算法是计算机科学的一大全新分支——“不情愿”算法学——的研究成果的一大代表。所谓“不情愿”算法学,也就是设计与分析“不情愿”算法的学科。

直觉上讲,一个关于问题 \(P\)不情愿算法是指在所有算法当中,被人为设计出来用于故意拖延时间并且能够骗过略懂编程的人的算法。

最短路径问题

咕咕咕

慢速排序

显而易见地,没有任何一个算法能够比给 \(n\) 个数按大小排序更能清晰地体现我们“不情愿”算法学的优雅与强大。排序问题有着相当久远的历史,它可以一直向前追溯到远于我们在上周三的下半天决定创建“不情愿”算法学。感谢我们之前勤奋刻苦的先驱们的工作,排序算法的时间简化度从归并排序的 \(\Omega(n\log n)\) 逐步降低到希尔排序的 \(\Omega(n\sqrt{n})\)(只要适当选取增量就可以达到),冒泡排序的 \(\Omega(n^2)\),并最终,由本特利在《编程珠玑》中提出了相当巧妙的 \(\Omega(n^3)\) 排序算法。

http://www.hskmm.com/?act=detail&tid=33209

相关文章:

  • DIVCNT
  • 3. JVM 运行时数据区
  • 软工学习日志
  • Pixelium Design:Vue3 的像素风 UI 组件库
  • 修电脑不求人:AI智能修复电脑工具的体验分享
  • 效率与安全双升:AI许可证识别重塑医药行业合规流程
  • Spring BeanPostProcessor 前置处理 afterPropertiesSet BeanPostProcessor 后置处理区别
  • Xcode上编译调试ffmpeg - 详解
  • 最新版Origin 2025b安装包下载及详细安装教程,附永久免费中文汉化破解版Origin安装包
  • 第十七篇
  • 《程序员修炼之道》阅读笔记1
  • Unity3D中定义全局宏(不同于在unity设置中的)
  • AtCoder arc208 总结
  • OOP - 实验一
  • 题解:qoj8329 Excuse
  • `uv run pytest` does not work
  • VMware17.6图文安装教程(附安装包)VMware17.6
  • Sourcetree - Git 备份
  • uni-app x实现上下拉动,动态加载数据
  • HyperWorks许可状态监控工具
  • mysql删除数据表某个日期之前的数据
  • KMP算法
  • 企业微信ipad协议稳定防封的最新最全功能
  • 企业微信协议ipad,稳定防封私有化部署私域流量聚合聊天,机器人实现方案
  • 重新思考钓鱼攻击意识培训:网络安全的关键反思
  • 任务分解与小模型如何降低AI成本
  • spring事件监听的核心机制
  • 直播软件开发搭建公司
  • freeswitch的proxy_media模式下video流的问题与修正
  • DNS 相关