【发布时间】:2015-03-26 20:23:29
【问题描述】:
我面临以下问题:
-
我有一个巨大的文件(比如 30 GB),它使用特定的 API 在内存中流式传输。
此 API 仅允许我向前(而不是向后)阅读。但是这些文件可以读取任意多次。
该文件包含几乎所有已排序的数据,例如,99% 的数据已排序,但可能会发生记录不在其正确位置,并且如果所有内容都已排序,则应该在很早之前插入.
我正在尝试创建此文件的副本,但需要对其进行排序。
有没有优雅的方法来做到这一点?
我能想到的唯一方法是最通用的方法:
- 读取文件
- 创建一批几 GB 的内存,对它们进行排序,将它们写入 HDD 上的文件
- 使用外部合并将所有这些临时文件合并到最终输出中
但是,这并没有使用数据“几乎”排序的特性。会有更好的方法来做到这一点吗?例如不使用硬盘上的外部文件?
【问题讨论】:
-
似乎微不足道 - 将元素放在 300 MB 优先级队列中,然后合并。问题在哪里?
-
搜索(外部)归并排序。它将数据切割成可管理的块,单独对每个块进行排序,然后将所有块合并在一起。
-
这是我在问题末尾提出的建议,但是我想知道是否有一种方法可以更好地了解我的数据结构是特定的
-
您会发现,使用替换选择分发传递时,您最终可能只会合并两个文件,甚至可能只有一个,如果输入已经几乎排序的话。
-
如果所有乱序元素都出现在它们应该出现的位置之后,您可以直接遍历文件,将其拆分为已排序和未排序的部分(未排序的元素只是那些比最近看到的已排序子集的元素小),对未排序的部分进行排序(考虑到它非常小,这应该不是问题),然后将两者合并。
标签: c++ algorithm sorting optimization