📅  最后修改于: 2021-01-12 03:34:10             🧑  作者: Mango
将一组不同长度的分类文件合并为一个分类文件。我们需要找到一个最佳解决方案,在该解决方案中,将在最短的时间内生成结果文件。
如果给出了已排序文件的数量,则有许多方法可以将它们合并为一个已排序文件。可以成对执行此合并。因此,这种类型的合并称为2向合并模式。
由于不同的配对需要不同的时间,因此在此策略中,我们希望确定将多个文件合并在一起的最佳方式。在每个步骤中,将合并两个最短的序列。
合并一个p记录文件和一个q记录文件可能需要p + q个记录移动,最明显的选择是在每个步骤中将两个最小的文件合并在一起。
双向合并模式可以用二进制合并树表示。让我们考虑一组n个排序文件{f 1 ,f 2 ,f 3 ,…,f n } 。最初,它的每个元素都被视为单节点二叉树。为了找到最佳解决方案,使用了以下算法。
Algorithm: TREE (n)
for i := 1 to n – 1 do
declare new node
node.leftchild := least (list)
node.rightchild := least (list)
node.weight) := ((node.leftchild).weight) + ((node.rightchild).weight)
insert (list, node);
return least (list);
在该算法的最后,根节点的权重代表了最佳成本。
让我们考虑给定的文件f 1 ,f 2 ,f 3 ,f 4和f 5分别具有20、30、10、5和30个元素。
如果按照提供的顺序执行合并操作,则
M 1 =合并f 1和f 2 => 20 + 30 = 50
M 2 =合并M 1和f 3 => 50 + 10 = 60
M 3 =合并M 2和f 4 => 60 + 5 = 65
M 4 =合并M 3和f 5 => 65 + 30 = 95
因此,操作总数为
50 + 60 + 65 + 95 = 270
现在,出现问题了,还有没有更好的解决方案?
根据数字的大小按升序对它们进行排序,我们得到以下序列-
f 4 ,f 3 ,f 1 ,f 2 ,f 5
因此,可以在此序列上执行合并操作
M 1 =合并f 4和f 3 => 5 + 10 = 15
M 2 =合并M 1和f 1 => 15 + 20 = 35
M 3 =合并M 2和f 2 => 35 + 30 = 65
M 4 =合并M 3和f 5 => 65 + 30 = 95
因此,操作总数为
15 + 35 + 65 + 95 = 210
显然,这比上一个更好。
在这种情况下,我们现在将使用此算法解决问题。
因此,该解决方案需要15 + 35 + 60 + 95 = 205个比较数。