通过使用最小交换交换相邻元素来对序列进行排序

2023-12-15

我们有一个未排序的 N 个数字序列(1,2,3,4,...N)。我们可以通过按特定顺序交换相邻元素来对整个序列进行排序。给定一个序列,如何计算对序列进行排序所需的最小可能交换。

作为示例,请考虑序列 {4, 2, 5, 3, 1}。

对此进行排序的最佳方法是按以下顺序使用 7 次交换

  1. 交换 3, 1:{4, 2, 5, 1, 3}
  2. 交换 5, 1:{4, 2, 1, 5, 3}
  3. 交换 4、2:{2, 4, 1, 5, 3}
  4. 交换 4, 1:{2, 1, 4, 5, 3}
  5. 交换 2, 1:{1, 2, 4, 5, 3}
  6. 交换 5、3:{1, 2, 4, 3, 5}
  7. 交换 3、4:{1, 2, 3, 4, 5}

贪心算法并没有被证明是有效的。反例很容易构建。接近解决方案的下一个明显选择是动态编程。

假设我们有一个未排序的序列:{A1, A2, ...Ai, A(i+1), ..., An}。我们知道对序列 {Ai, A(i+1), ..., An} 进行排序所需的最小交换次数为 Min[Ai, A(i+1), ..., An}。问题是找到 Min[A(i-1), Ai, ..., An]。

好吧,我脑海中浮现的第一个想法就是添加将 A(i-1) 放在已排序序列 {Ai, ..., An} 中的正确位置所需的步骤数。这是可行的:问题中给出的示例已使用完全相同的方法解决。

但我无法证明这个解决方案的有效性。我经常遇到这种情况。当我认为我已经解决了问题时,我能做的最好的事情就是获得一个“直观”的证明。我正在上高中,没有接受过算法方面的正式培训。我这样做纯粹是出于兴趣。

有没有严格的数学符号可以将这个问题转化为形式化证明?这个表示法可以推广到其他问题吗?如何?如果它能以高中生可以理解的形式呈现,我将不胜感激。


This is a classical algorithm problem. The minimum number of swaps is equal to the number of inversions in the array. If we have index i and index j such that ai > aj and i < j then this is called an inversion. Let's prove this statement! I will need a few lemmas on the way:

Lemma 1: If there is no inversion of two adjacent elements then the array is sorted.
Proof: Let's assume that no two adjacent elements form an inversion. This means that ai <= ai+1 for all i in the interval [0, n-1]. As <= is transitive this will mean that the array is sorted.

Lemma 2: A single swap of two adjacent elements will reduce the total number of inversions in the array by at most 1.
Proof: when we swap two adjacent elements ai and ai+1 their relative position with respect to all the other elements in the array will remain unchanged. That is for all elements that were after ai+1, they will still be after ai+1 and for all elements before ai, they will still be before the ai. This also means that if ai or ai+1 formed an inversion with an element aj then, they will still form an inversion with it after the swap. Therefor if we swap ai and ai+1 we will affect only inversions that these two elements used to form. As two elements may participate in no more than one inversion we have also proved the lemma.

Lemma 3:我们需要至少对相邻元素执行 NI 交换才能对数组进行排序,其中 NI 是数组中反转的次数
Proof:在排序数组中没有反转。同样根据引理 2,单次交换最多可以减少 1 次反转次数。因此,我们需要执行的交换次数至少与反转次数一样多。

Lemma 4:我们总是可以对相邻元素执行 NI 交换来对数组进行排序,就像上面一样,NI 是数组中反转的次数。
Proof:如果我们假设数组中两个相邻元素没有反转,那么根据引理 1,数组将被排序,我们就完成了。
否则,至少有一对相邻元素形成反转。我们可以交换它们,从而将反转总数减少一次。我们可以继续执行这个操作恰好 NI 次。

现在我已经从答案开始证明了我的说法。

剩下的唯一问题是如何计算给定数组中的反转次数。您可以通过稍微修改合并排序来实现这一点,在合并阶段累积反转。你可以看看这个答案有关如何实施的详细信息。算法的总体复杂度为O(n*log(n)).

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

通过使用最小交换交换相邻元素来对序列进行排序 的相关文章

  • 从列表中选择项目以求和

    我有一个包含数值的项目列表 我需要使用这些项目求和 我需要你的帮助来构建这样的算法 下面是一个用 C 编写的示例 描述了我的问题 int sum 21 List
  • 二分插入排序和复杂度

    我有一个关于在插入排序算法中使用二分搜索的简单问题 更准确地说 在通常的插入排序的每一步中 我们不是将元素与前一个 已排序 子数组中的所有元素进行线性比较 而是在该已排序子数组中使用二分搜索来查找该元素所属的位置 我知道这减少了算法进行的比
  • 如何在javascript中计算日出和日落?

    我正在使用appcelerator titan开发一个IOS应用程序 我想让我的应用程序在日出和日落时向用户发送本地通知 解决这个问题的一个好工具是使用 YQL 的雅虎天气 但是 雅虎天气仅供非商业用途 我正在尝试找到一个javascrip
  • 最小硬币找零问题——回溯

    我正在尝试用最少数量的硬币解决硬币找零问题 采用回溯法 我实际上已经完成了它 但我想添加一些选项 按其单位打印硬币数量 而不仅仅是总数 这是我下面的Python代码 def minimum coins coin list change mi
  • 另一个生命游戏问题(无限网格)?

    我一直在玩 Conway 的生命游戏 最近发现了一些令人惊讶的快速实现 例如 Hashlife 和 Golly 在这里下载Golly http golly sourceforge net http golly sourceforge net
  • 需要创建一个“选择你自己的冒险”类型的指南 - 最佳使用方法

    基本上需要询问用户一系列问题并收集信息 每个问题都可能对以后的不同问题产生影响 另一个例子是涡轮税的网络界面 在某些 上回答 是 可能会引发未来的问题 似乎这在软件中是一个相当常见的问题 所以我想我是在问是否有任何现有的解决方案 设计模式可
  • 验证是否存在唯一字符串的组合

    class Details String name String age String email String location 1 如果有详细信息列表 如下所示List
  • 解决复发问题

    我被给予F 0 X and F i A F i 1 2 B F i 1 C 1000000 for 1 i N 现在给出N A B C and X 如何找到所有N元素有效吗 我需要将这 N 个元素分成 2 个集合 其中最大的元素在第一个集合
  • O(log n) 总是比 O(n) 快吗

    如果有 2 种算法以不同的复杂度计算相同的结果 O log n 总是会更快吗 如果是这样请解释一下 顺便说一句 这不是作业问题 不会 如果一种算法运行在N 100另一个在 log N 100 那么对于较小的输入大小 第二个将会较慢 渐近复杂
  • 匈牙利算法 - 系统分配

    我正在一个项目中实现匈牙利算法 我设法让它工作 直到所谓的步骤 4维基百科 http en wikipedia org wiki Hungarian algorithm Matrix 5Finterpretation 我确实设法让计算机创建
  • 拓扑排序卡恩算法 BFS 或 DFS

    拓扑排序的方法是BFS还是DFS 哪个正确 我认为BFS是对的 但有些网站说DFS 有些网站说BFS 我很困惑 卡恩算法与 BFS 或 DFS 相同吗 或者BFS 或DFS 只是卡恩算法的工具 Kahn算法和DFS在实践中都用于拓扑排序 选
  • 计算序列 1,3,8,22,60,164,448,1224... 的第 n 项? [复制]

    这个问题在这里已经有答案了 可能的重复 我想以 Order 1 或 nlogn 的顺序生成序列 1 3 8 22 60 164 的第 n 项 https stackoverflow com questions 11301992 i want
  • 多线程归并排序,添加额外的线程

    我在java中的多线程合并排序算法中面临一个问题 我应该将代码修改为 3 4 5 6 7 8 线程合并排序 将原始数组划分为subArrays 目前它有2subArrays 如何将原始数组拆分为 3 4 5 6 7 8subArray是为了
  • 递归最长递增子序列的记忆

    我为最长递增子序列提出了简单的以下递归解决方案 但是 您可以帮助将记忆包含到这个递归解决方案中吗 public int findLIS int a int maxSoFar int item int count if item a leng
  • LRU、FIFO、随机

    当出现页面错误或缓存未命中时 我们可以使用最近最少使用 LRU 先入先出 FIFO 或随机替换算法 我想知道 哪一个提供了最好的性能 也称为未来缓存丢失 页面错误最少的可能性 架构 Coldfire 处理器 没有愚蠢的问题 这句话非常适合这
  • n维匹配算法

    在这里寻求一些建议 有谁知道在 n 维空间中开始研究匹配算法的好地方 例如 任何约会网站都必须使用某种算法来匹配 2 个人 我读到的是 我们可以将一个人的特征映射到一个 n 维数组中 每个特征都有一个点系统 一旦我们拥有一个人的所有 可用
  • 我想知道像tineye.com这样的反向图像搜索服务是如何工作的......?

    像 TinEye 这样的反向图像搜索引擎如何工作 我的意思是进行图像搜索需要哪些参数 不知道 TinEye 是否使用这个 但是SURF http en wikipedia org wiki SURF是用于此目的的常用算法 在这里您可以看到一
  • 高效编写航空公司路由算法

    Given 航班数据库 出发城市 到达城市 出发时间 到达时间 问题 如果出发时间不重要 那么在两个城市之间列出服务的最有效算法是什么 考虑到我们想要最小化中途停留时间 但仍高于标称最小值 即 20 分钟 并最小化中途停留次数 如果有直达航
  • 查找预排序数组中给定值的最低索引

    嘿 我在采访中遇到了这个问题 想知道解决它的最佳方法是什么 假设给定一个已经排序的数组 并且您想要找到某个值 x 的最低索引 这是我想出的 python 伪代码 我只是想知道是否有更好的方法来实现它 def findLowestIndex
  • 带提示的二分查找

    我有一个简单的std vector包含一些已排序的数字 按升序 我想查找一个元素 到目前为止我使用 return std lower bound vec begin vec end needle Where needle是我寻找的元素 然而

随机推荐