vb.net 按对象属性排序列表(对象)
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/38993071/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Sort List(of Object) by object properties
提问by Mech_Engineer
I'm trying to achieve something where the answer is already given for. But it's in c#and I don't have any knowledge what-so-ever over c#so I'm looking for a vb.net alternative.
我正在努力实现一些已经给出答案的东西。但它在里面c#,我对过去的事情一无所知,c#所以我正在寻找 vb.net 替代品。
I made a classcalled BomItemwhich has several properties like quantity, description etc.
我做了一个class调用BomItem,它有几个属性,比如数量、描述等。
I add these BomItemsinto a List(of BomItem)but now I would like to sort them according to a property. How can you sort the items based on the ItemNumberproperty?
我将这些添加BomItems到 aList(of BomItem)但现在我想根据属性对它们进行排序。您如何根据ItemNumber属性对项目进行排序?
Here is the linkto the c#solution I found.
这是我找到的解决方案的链接c#。
My class code
我的班级代码
Public Class BomItem
Public Property ItemNumber As String
Public Property Description As String
Public Property Quantity As Double
Public Property Material As String
Public Property Certificate As String
End Class
How I add the BomRowobjects
我如何添加BomRow对象
_NewBomList.Add(New BomItem() With {
.ItemNumber = oRow.ItemNumber,
.Description = oPropSet.Item("Description").Value,
.Quantity = oRow.TotalQuantity,
.Material = oPropSet.Item("Material").Value,
.Certificate = CustomPropertySet.Item("Cert.").Value})
Comparer
比较器
Public Class NaturalSort
Implements IComparer
Public Function Compare(ByVal x As Object,
ByVal y As Object) As Integer Implements IComparer.Compare
' [1] Validate the arguments.
Dim s1 As String = x
If s1 = Nothing Then
Return 0
End If
Dim s2 As String = y
If s2 = Nothing Then
Return 0
End If
Dim len1 As Integer = s1.Length
Dim len2 As Integer = s2.Length
Dim marker1 As Integer = 0
Dim marker2 As Integer = 0
' [2] Loop over both Strings.
While marker1 < len1 And marker2 < len2
' [3] Get Chars.
Dim ch1 As Char = s1(marker1)
Dim ch2 As Char = s2(marker2)
Dim space1(len1) As Char
Dim loc1 As Integer = 0
Dim space2(len2) As Char
Dim loc2 As Integer = 0
' [4] Collect digits for String one.
Do
space1(loc1) = ch1
loc1 += 1
marker1 += 1
If marker1 < len1 Then
ch1 = s1(marker1)
Else
Exit Do
End If
Loop While Char.IsDigit(ch1) = Char.IsDigit(space1(0))
' [5] Collect digits for String two.
Do
space2(loc2) = ch2
loc2 += 1
marker2 += 1
If marker2 < len2 Then
ch2 = s2(marker2)
Else
Exit Do
End If
Loop While Char.IsDigit(ch2) = Char.IsDigit(space2(0))
' [6] Convert to Strings.
Dim str1 = New String(space1)
Dim str2 = New String(space2)
' [7] Parse Strings into Integers.
Dim result As Integer
If Char.IsDigit(space1(0)) And Char.IsDigit(space2(0)) Then
Dim thisNumericChunk = Integer.Parse(str1)
Dim thatNumericChunk = Integer.Parse(str2)
result = thisNumericChunk.CompareTo(thatNumericChunk)
Else
result = str1.CompareTo(str2)
End If
' [8] Return result if not equal.
If Not result = 0 Then
Return result
End If
End While
' [9] Compare lengths.
Return len1 - len2
End Function
End Class
回答by Alex B.
_NewBomList.OrderBy(Function(bi) bi.ItemNumber)
and for descending:
和下降:
_NewBomList.OrderByDescending(Function(bi) bi.ItemNumber)
If you want a numeric order in your string you have to convert it to an integer first:
如果您想在字符串中使用数字顺序,则必须先将其转换为整数:
_NewBomList.OrderBy(Function(bi) Integer.Parse(bi.ItemNumber))
Edit:
To provide a custom IComparerfor the OrderBy extension you have to create a class which implements IComparer(Of String)where String are your ItemNumbersto compare:
编辑:
要为IComparerOrderBy 扩展提供自定义,您必须创建一个类来实现IComparer(Of String)您ItemNumbers要比较的String :
Class ItemNumberComparer
Implements IComparer(Of String)
Public Function Compare(String x, String y)
Dim ix As String() = x.Split("."C)
Dim iy As String() = y.Split("."C)
Dim maxLen As Integer = Math.Max(ix.Length, iy.Length)
For i As Integer = 0 To maxLen - 2
If ix.Length >= i AndAlso iy.Length >= i Then
If Integer.Parse(ix(i)) < Integer.Parse(iy(i)) Then
Return -1 'If x.i is LT y.i it must be smaller at all
ElseIf Integer.Parse(ix(i)) > Integer.Parse(iy(i)) Then
Return 1 'If x.i is GT y.i it must be bigger all
End If
End If
Next
'This code is only executed if x and y differ at last number or have different ′number of dots
If ix.Length = iy.Length Then
Return Integer.Parse(ix(ix.Length - 1)).CompareTo(Integer.Parse(iy(iy.Length - 1))) 'Only last number differs
Else
Return ix.Length.CompareTo(iy.Length) 'The number with more dots is smaller
End If
End Function
End Class
Call syntax:
调用语法:
Dim comparer = new ItemNumberComparer()
_NewBomList.OrderByDescending(Function(bi) bi.ItemNumber, comparer)
回答by jmcilhinney
This C# code from that other thread:
来自该其他线程的此 C# 代码:
List<Order> SortedList = objListOrder.OrderBy(o=>o.OrderDate).ToList();
equates to this VB code:
相当于这个VB代码:
List(Of Order) SortedList = objListOrder.OrderBy(Function(o) o.OrderDate).ToList()
As you can see, very little changes. You just have to know the syntax for generics and lambda expressions.
如您所见,变化很小。你只需要知道泛型和 lambda 表达式的语法。
You should be aware, though, that this code does NOT sort your list. It sorts the items in the list and then adds them to a new list in that order. This is perfectly fine for many applications but if you're using that same list elsewhere then you won't see the new order there. While there are a few variations, one way to actually sort the list in place is like this:
但是,您应该知道,此代码不会对您的列表进行排序。它对列表中的项目进行排序,然后按该顺序将它们添加到新列表中。这对于许多应用程序来说非常好,但是如果您在其他地方使用相同的列表,那么您将看不到那里的新订单。虽然有一些变化,但实际对列表进行排序的一种方法是这样的:
objListOrder.Sort(Function(o1, o2) o1.OrderDate.CompareTo(o2.OrderDate))
回答by Martin Verjans
Another solution would be to implement the IComparable(see MSDN ref) interface. This interface is designed to sort your objects on a custom way :
另一种解决方案是实现IComparable(参见 MSDN 参考)接口。此界面旨在以自定义方式对您的对象进行排序:
Public Class BomItem
Implements IComparable
Public Property ItemNumber As String
Public Property Description As String
Public Property Quantity As Double
Public Property Material As String
Public Property Certificate As String
Public Function CompareTo(obj As Object) As Integer
Dim bom = CType(obj, BomItem)
If Not bom Is Nothing then
Return Me.ItemNumber.CompareTo(bom.ItemNumber)
Else
Throw New ArgumentException("Object is not a BomItem")
End If
End Class
and you can sort the list this way :
你可以用这种方式对列表进行排序:
Dim myList As New List(Of BomItem)
'Code to add your BomItems
myList.Sort()
This will actually sort your list, it does not create a new list.
这实际上会对您的列表进行排序,它不会创建新列表。

