. net 3.5和.net 4.0在排序方面的差异
本文关键字:net 方面 排序 | 更新日期: 2023-09-27 18:03:14
我遇到过。net框架的一个非常奇怪的行为,当排序一个集合时。这种行为在。net 3.5和。net 4.0之间是不同的(但我想我知道为什么),但更重要的是(这是我在这里真正关心的),在同一框架上的不同机器上的行为是不同的。
<<h2>上下文/h2>我正在开发一个依赖于第三方软件的软件(spring.net在这种情况下,但这并不重要),在某些时候,它正在排序一个集合,它的所有项目"相等"(比较器总是返回0)。这是不是在我的控制下,如果排序列表的行为总是一致的,我会很好。它不是。
如何复制
在。net 3.5中创建一个简单的项目,并运行下面的代码。当在3.5中编译时,行为似乎是一致的,并且集合将被"反转"(它出现为Three, Two, One)。现在,请将项目目标更改为。. NET 4 (不是4.5),并再次运行:在我的机器上,它不再反转集合(One, Two, Three),但在其他一些同事的机器上,它可以(Three, Two, One)!!我们有完全相同的设置…你能告诉我,在你的机器上,在4.0下,它是哪个吗?反转还是不反转?
我正在试着评估我的设置是否正确。
概念证明
class Program
{
static void Main()
{
var collection = new ArrayList
{
"One",
"Two",
"Three",
};
// It should in any case write One, Two, Three
Console.Out.WriteLine("Before sort: ");
foreach (string item in collection)
{
Console.Out.WriteLine("'t"+item);
}
collection.Sort(new OrderComparator());
// In .NET 3.5, it will write Three, Two, One
// In .NET 4, it will sometimes write Three, Two, One, sometimes One, Two, Three: what is it for you?
Console.Out.WriteLine("After sort: ");
foreach (string item in collection)
{
Console.Out.WriteLine("'t" + item);
}
Console.Out.WriteLine("--end--");
Console.Read();
}
}
public class OrderComparator : IComparer
{
public virtual int Compare(object o1, object o2)
{
return 0;
}
}
另外,如果你知道为什么会发生这种情况,请告诉我!
由ArrayList.Sort()完成的排序是不稳定的,因此你不能预测"相同"项的排序顺序。
此外,因为ArrayList.Sort()可能使用随机机制来选择快速排序算法的枢轴,相同的项可能在不同的PC上排序不同,甚至在同一台PC上。
[编辑:我找不到在当前实现中选择随机枢轴的任何证据,但数组排序仍然不稳定。我猜随机性来自TrySZSort()
的本机代码快速排序实现,这可能被称为。]
同样出于兴趣,Reflector在ArrayList.Sort()中显示了这段代码(如果您深入研究一下):
internal void Sort(int left, int length)
{
if (BinaryCompatibility.TargetsAtLeast_Desktop_V4_5)
{
this.IntrospectiveSort(left, length);
}
else
{
this.DepthLimitedQuickSort(left, (length + left) - 0x1, 0x20);
}
}
,它似乎为。net 4.5选择了一个完全不同的排序算法。