在c++中合并8个排序列表,我应该使用哪种算法
我有 8 个排序列表,需要将其合并为 1 个排序列表。 我不知道最好的方法来做到这一点。 我在想以下问题:
void merge_lists_inplace(list<int>& l1, const list<int>& l2)
{
list<int>::iterator end_it = l1.end();
--end_it;
copy(l2.begin(), l2.end(), back_inserter(l1));
++end_it;
inplace_merge(l1.begin(), end_it, l1.end());
}
list<int> merge_8_lists(list<int>[8] lists)
{
merge_lists_inplace(lists[0], lists[1]);
merge_lists_inplace(lists[2], lists[3]);
merge_lists_inplace(lists[4], lists[5]);
merge_lists_inplace(lists[6], lists[7]);
merge_lists_inplace(lists[0], lists[2]);
merge_lists_inplace(lists[4], lists[6]);
merge_lists_inplace(lists[0], lists[4]);
return lists[0];
}
但是最后再担心排序会不会更好?
list<int> merge_8_lists(list<int>[8] lists)
{
for (int i = 1; i < 8; ++i)
copy(lists[i].begin(), lists[i].end(), back_inserter(lists[0]));
lists[0].sort();
return lists[0];
}
旁注:我不在乎列表是否被修改。
I have 8 sorted lists that I need to merge into 1 sorted list. I don't know the best way to do this. I was thinking of the following:
void merge_lists_inplace(list<int>& l1, const list<int>& l2)
{
list<int>::iterator end_it = l1.end();
--end_it;
copy(l2.begin(), l2.end(), back_inserter(l1));
++end_it;
inplace_merge(l1.begin(), end_it, l1.end());
}
list<int> merge_8_lists(list<int>[8] lists)
{
merge_lists_inplace(lists[0], lists[1]);
merge_lists_inplace(lists[2], lists[3]);
merge_lists_inplace(lists[4], lists[5]);
merge_lists_inplace(lists[6], lists[7]);
merge_lists_inplace(lists[0], lists[2]);
merge_lists_inplace(lists[4], lists[6]);
merge_lists_inplace(lists[0], lists[4]);
return lists[0];
}
But would it be better to just worry about the sorting last?
list<int> merge_8_lists(list<int>[8] lists)
{
for (int i = 1; i < 8; ++i)
copy(lists[i].begin(), lists[i].end(), back_inserter(lists[0]));
lists[0].sort();
return lists[0];
}
Side note: I don't care that the lists are modified.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(6)
合并排序合并阶段的简单扩展可以在 O(n lg m) 时间内完成此操作(其中 n = 项目总数,m = 列表数量),使用 优先级队列(例如,堆)。 伪代码:
以及 C++ 中的简单(未经测试!)具体实现:
A simple extension of merge sort's merge phase can do this in O(n lg m) time (where n = total number of items and m = number of lists), using a priority queue (eg, a heap). Pseudocode:
And a simple (untested!) concrete implementation in C++:
您可以尝试一次对每个列表应用合并排序:
http://en.wikipedia .org/wiki/Merge_sort
这里有合并排序的算法。 本质上,您将使用列表 1 和 2 并对它们进行合并排序。 然后,您将采用新的组合列表并使用列表 3 进行排序,如此继续下去,直到获得一个完全排序的列表。
编辑:
实际上,因为您的列表已经排序,所以只需要合并排序的最后一部分。 我会迭代地将列表组合成越来越大的部分,同时对每个较大的列表进行排序,直到获得完整的列表,这本质上就是合并排序在完成分而治之方法后所做的事情。
You could try applying the merge sort one at a time to each of the lists:
http://en.wikipedia.org/wiki/Merge_sort
This has the algorithm for the merge sort. Essentially you'd go with list 1 and 2 and merge sort those. Then you'd take that new combined list and sort with list 3, and this continues until you have one fully sorted list.
EDIT:
Actually, because your lists are already sorted, only the last part of the merge sort would be needed. I would iteratively combine the lists into bigger and bigger parts all the while sorting each of those bigger lists until you have your full list, which is essentially what the merge sort does after it's done with its divide and conquer approach.
如果性能不是问题,我会最后对列表进行排序。 代码更具可读性、更短,并且不太可能被将来重新访问代码的人搞砸。
If performance is not a concern, I would sort the lists last. The code is more readable, shorter, and less likely to get screwed up by someone revisiting the code in the future.
这是标准(尽管是 8 路)合并排序。
基本上,您“打开”八个排序列表,然后开始处理它们,每次提取最低值,例如
:
This is a standard (although 8-way) merge sort.
Basically you "open" the eight sorted lists then begin processing them, extracting the lowest value each time, something like:
基本上你正在做多路合并排序的一部分,除了你的东西已经排序了......
http://lcm.csa.iisc.ernet.in/dsa/node211.html
只需找到每个数组中最低的(几乎用作堆栈)并将其放入输出中,直到所有堆栈为空...
Basically you are doing part of multiway mergesort, except your stuff is already sorted...
http://lcm.csa.iisc.ernet.in/dsa/node211.html
Just find the lowest in each array (almost use as stacks) and put that in your output till all stacks are empty...
您需要合并排序。 您的列表已经拆分,但并未一直拆分到最小级别。 您可能想要这样做:
这不应该是一个耗时/内存消耗的操作,因为串联应该添加从列表中的最后一个节点到下一个列表的第一个元素的链接。
You want a merge sort. Your lists are already split but not all the way to the smallest level. You may want to do this:
That shouldn't be a time/memory consuming operation because the concatenation should add a link from the last node in in a list to the first element of the next list.