是否按多个标准进行快速排序
Make QuickSort sort by multiple criteria?
是否有按多个条件进行快速排序的方法?例如,我有一组边。每条边都有一个源、目的地和长度。我想先把长度较小的边放在我的数组中。但如果长度相同,我想用一个较小的源顶点进行排序。如果这些源顶点相同,我想按两个目标顶点中较小的一个进行排序。
例如:
4(来源)2(目的地)3(长度)
1(来源)5(目的地)3(长度)
由于它们都有相同的长度,我们来看源顶点。由于第二条边比第一条边小,我们交换它们,因为我们按源顶点进行比较。
下面是我的快速排序,老实说,我不确定为什么它没有正确排序。如果有一种方法可以降低快速排序的效率,但更稳定,我很乐意接受建议!
void quickSort(edge *e, int left, int right)
{
int i = left, j = right;
int temp, temp1, temp2;
int pivot = (left + right)/2;
while(i <= j)
{
while(e[i] < e[pivot])
i++;
while(e[pivot] < e[j])
j--;
if(i <= j)
{
temp = e[i].getLength();
temp1 = e[i].getEdgeSrc();
temp2 = e[i].getEdgeDes();
e[i].setLength(e[j].getLength());
e[i].setEdgeSrc(e[j].getEdgeSrc());
e[i].setEdgeDes(e[j].getEdgeDes());
e[j].setLength(temp);
e[j].setEdgeSrc(temp1);
e[j].setEdgeDes(temp2);
i++;
j--;
} //if statement
}///while loop
if(left < j)
quickSort(e, left, j);
if(i < right)
quickSort(e, i, right);
}
我的条件排序:
bool edge::operator<(const edge &other) const
{
if (length < other.length)
return true;
else if ((length == other.length) && (source < other.source))
return true;
else if((length == other.length) && (source == other.source) && (destination < other.destination))
return true;
return false;
}
同样,如果有人知道如何通过降低时间复杂性但使其稳定来正确地进行快速排序,我很乐意接受任何建议!非常感谢。有什么帮助吗?
编辑:这就是我调用快速排序的方式。我根据读取的边数调用它。
quickSort(e, 0, edges-1); //-1 because if you put in edges, it'd go past the bounds of the array
编辑:当我试图在我的算法中加入这样的东西时:
0 1 1
0 3 1
1 3 1
2 5 1
4 10 1
4 8 1
10 8 1
11 6 2
11 7 2
6 7 1
9 6 1
9 7 1
这是输出:
0 1 1
0 3 1
1 3 1
2 5 1
4 8 1
4 10 1
6 7 1
6 9 1
8 10 1<-应低于7 9 1
7 9 1<-应高于8 10 1
6 11 2
7 11 2
这样写更干净
if (length != other.length)
return length<other.length;
if ( source != other.source)
return source < other.source;
return destination < other.destination;
您还应该能够执行temp = e[i]
等操作,因为成员都是int。
我认为这(以及你提交的代码)应该可以完成你想要的任务。
如果你有稳定性问题,那是因为快速排序不稳定。你可以通过添加更多的条件来避免lhs==rhs
的发生。或者,您可以尝试Mergesort
坦率地说,我对Quick排序没有太多经验,但你的impl看起来确实与Wikipedias原地算法明显不同。例如,您的枢轴根本不移动。你能检查一下是否有问题吗?
编辑
查看您的链接后
看起来链接的算法也将pivot用作值,而不是索引(就像您所做的那样)。它在语法上看起来与您的相同,直到您考虑到您的枢轴值可能会移动,之后您的枢轴索引将指向其他
int pivot = arr[(left + right) / 2];
这有帮助吗?
EDIT:以下是就地快速排序的伪代码:http://en.wikipedia.org/wiki/Quicksort#In-位置版本
这与代码的不同之处在于,数据透视是一个值(左右值的平均值),而不是一个索引。
如果您正在寻找一个简单的非最优解决方案,请按目标顶点合并整个列表,然后按原点顶点合并整个名单,然后按边长度合并整个名单。这利用了mergesort是一种稳定的排序算法,并且运行时间为边数O(E)的事实。
- 如何修复我的快速排序实现?
- C++运行时错误与快速排序算法抛出堆栈转储错误
- 在 MIPS 中快速排序
- 不正确的比较和交换计数器输出用于快速排序功能
- 使用 std::vector C++快速排序,EXC_BAD_ACCESS代码 2
- 使用快速排序对 C++ 中的可视化工具错误进行排序
- 快速排序 - 三个中位数枢轴选择 - 某些元素顺序不正确
- 快速读取标准输入缓冲区,无需检查
- 并行快速排序分区中的隔离错误
- 实现 3 路分区以实现快速排序
- 为什么这个快速排序实现给出了一个奇怪的输出
- 我的快速排序在对预排序的项目进行排序时失败,如何改进?
- 快速排序不适用于大型数组
- 快速排序;分段错误,但找不到位置?
- 快速排序函数在快速排序算法中如何工作?
- 3路随机快速排序分区功能
- 在最坏的情况下试验快速排序.它运行良好,但在最坏的情况下发生未知错误.我想
- 当给出预先排序的输入时,为什么我的快速排序实现很慢
- 我想要一个改变数组快速排序的2个数字的函数
- 是否按多个标准进行快速排序