【发布时间】:2015-08-16 13:29:42
【问题描述】:
我正在尝试覆盖列表框中的排序方法以按降序排序。
代码:
public CustomSortListBox()
: base()
{
}
protected override void Sort()
{
if (this.Items.Count > 1)
{
bool swapped;
do
{
int counter = this.Items.Count - 1;
swapped = false;
while (counter > 0)
{
// set this to != to reverse sorting
if (this.Items[counter].ToString().CompareTo(this.Items[counter - 1].ToString()) != -1)
{
object temp = Items[counter];
this.Items[counter] = this.Items[counter - 1];
this.Items[counter - 1] = temp;
swapped = true;
}
counter -= 1;
}
}
while (swapped);
}
}
现在,我直观地期望每当将项目添加到列表时都会调用此方法,这似乎是当 ListBox.Sorted = true 时它与基本 ListBox 一起工作的方式。但是,在将项目添加到列表后使用我的 CustomSortListBox 时,我的自定义排序没有得到尊重,此外,当项目列表发生更改时,没有调用被覆盖的方法,甚至没有遇到断点。
然后我读到了这个https://gfaraj.wordpress.com/2008/07/31/custom-sorting-for-listbox-in-c/,上面写着“不要忘记只有在 Sorted 属性从 false 变为 true 时才会调用 Sort”这对我来说似乎很荒谬,但可以肯定的是,当切换 Sorted 并重新打开时,我的自定义排序被调用并工作。
有趣的是,在这之后,保留 Sorted = true,添加的新项目使用基本的 Sort() 方法进行排序,创建升序和降序项目的混合。直到您再次切换 Sorted false -> true。
我什至会接受将 Sorted = false; 设置为 hacky 的解决方案。排序=真;在 ItemsChanged 的事件处理程序中,但这样的事件不存在。
我做错了什么以及如何在添加列表时尊重此排序覆盖?
(我见过C#'s ListBox doesn't see my overrided Sort() method,但他的问题不清楚,似乎刚刚“消失”,他随机选择的答案并不理想,甚至由于无法访问保护级别而无法编译)
【问题讨论】:
-
不必从 MSDN 文章中复制粘贴代码。您可以指出您希望每次添加项目时都调用一些自定义
Sort方法 -
完全同意@SergeyBerezovskiy!关于这个“复制粘贴”问题(re:msdn.microsoft.com/en-us/library/…),我也想说同样的话。另外,问题海报到底在问什么?一些清晰会有所帮助。最好的问候,
-
查看 ListBox 源代码可以看到 Add 方法没有调用 Sort,它只是调用(内部)BinarySearch 方法来获取放置新项目的索引。所以覆盖排序将无济于事。但是为什么要对 ListBox 进行排序。对我来说,ListBox 是用来显示数据而不是对数据进行排序的东西。如果您想对某些内容进行排序,请将您的数据放入列表中,对该列表进行排序并将该列表绑定到 ListBox。
-
这种行为有据可查。它以这种方式工作是有充分理由的,本机 ListBox 控件保留自己的列表中显示的字符串的副本。因此,为了对它们进行排序,必须首先清空该列表,然后按照排序顺序重新添加已排序的项目。这非常昂贵,每次添加一个项目时都这样做的成本太高。
-
@SergeyBerezovskiy 这实际上与 MSDN 上的代码不同。但我明白你的意思,帖子中并不真正需要它。
标签: c# winforms sorting listbox