目前,我有一个List(of String),其中包含类似于:
的数据"207.5,1"
"373,2"
"278.5,3"
"134,4"
"277,5"
"674,7"
"58.5,9"
在此列表中,我应用了两个命令' list.Sort'然后' list.Reverse'两者都完全符合预期,我的列表包含:
"674,7"
"58.5,9"
"373,2"
"278.5,3"
"277,5"
"207.5,1"
"134,4"
正如你所看到的,无论出于何种意图和目的,这都是完美的,但是,目光敏锐的人会注意到这个条目" 58.5,9"不合适,应该在列表的底部。
我很欣赏我在这里排序字符串,所以我一定会失败。我需要发现的是,我如何将每行的字符串内容复制到另一个可排序的容器中,该容器存储我的数字和索引'作为整数和/或单身?理想情况下,我最终会得到一个数组或类似的数据:
674.0,7
373.0,2
278.5,3
277.0,5
207.5,1
134.0,4
58.5,9
我已经尝试了尽可能多的迭代(我对此很新,所以很可能错过了非常明显的!)。如果可以的话请帮忙!感谢。
答案 0 :(得分:1)
您可以使用LINQ执行您想要的操作。如果您只想按正确的顺序排序字符串,可以使用:
Dim input = {
"207.5,1",
"373,2",
"278.5,3",
"134,4",
"277,5",
"674,7",
"58.5,9"
}
Dim sorted =
From item In input
Let n = CDec(item.Split(","c)(0))
Order By n Descending
Select item
这只是将第一个数字转换为十进制数以用于排序。如果您想要提取两个数字的对象,可以使用:
Dim sorted2 =
From item In input
Let parts = item.Split(","c)
Select result = New With { .n = CDec(parts(0)), .idx = CInt(parts(1)) }
Order By result.n Descending
这为您提供了IEnumerable的具有n
和idx
属性的匿名类型 - 如果您不想要匿名类型,您可以创建一个类并创建它的实例(例如,您需要返回它来自一个功能)。
答案 1 :(得分:1)
至少就代码行而言,最简单的方法是使用允许Sort
的{{1}}重载。但是,如果您经常使用这些数值,则应考虑数据的类或结构。
我可以将每行的字符串内容复制到另一个可排序容器
问题不是容器,而是数据。数字字符串不按数值排序。
Comparer
用法:
Private Function ThingsCompare(x As String, y As String) As Int32
Dim xVal As Double = Convert.ToDouble(x.Split(","c)(0))
Dim yVal As Double = Convert.ToDouble(y.Split(","c)(0))
If xVal < yVal Then Return -1
If yVal < xVal Then Return 1
' equal, so compare segment 2
Dim xVal2 As Double = Convert.ToDouble(x.Split(","c)(1))
Dim yVal2 As Double = Convert.ToDouble(y.Split(","c)(1))
If xVal2 < yVal2 Then Return -1
If yVal2 < xVal2 Then Return 1
Return 0
End Function
鉴于以下数据:
things.Sort(AddressOf ThingsCompare)
(我添加了&#34; 9&#34;元素因为字符/数字排序高于所有其他元素)。结果:
9.1,1
9.1,9
58.5,9
134,4
207.5,1
277,5
278.5,3
373,2
674,7
答案 2 :(得分:1)
使用LINQ和Lambda表达式
Dim input = {
"207.5,1",
"373,2",
"278.5,3",
"134,4",
"277,5",
"674,7",
"58.5,9"
}
' orderedResult is a IOrderedEnumerable(Of String)
Dim orderedResult = input.
OrderByDescending(Function(item) CDec(item.Split(","c)(0)))
' dictResult is a Dictionary(Of Integer, Decimal)
' based on the sorted result
Dim dictResult = orderedResult.ToDictionary(
Function(item) CInt(item.Split(","c)(1)),
Function(item) CDec(item.Split(","c)(0)))
答案 3 :(得分:0)
如果您要多次使用数据,那么有一个代表它的类是有意义的。这样,您可以为部件提供有意义的名称,轻松创建新项目,轻松操作数据,并以自己的方式将其转换为字符串。
它可能看起来像一堆繁琐的代码,但你只需要编写一次,然后当你想要使用数据时,你的生活就会简单得多:
Option Infer On
Option Strict On
Module Module1
Public Class Datum
Property Number As Decimal
Property Index As Integer
Sub New()
' default constructor
End Sub
Sub New(NumberIndex As String)
Dim parts = NumberIndex.Split(","c)
' a simple parameter check
If parts.Length <> 2 Then
Throw New ArgumentException("No comma found in " & NameOf(NumberIndex))
End If
Number = CDec(parts(0))
Index = CInt(parts(1))
End Sub
Public Overrides Function ToString() As String
Return $"{Number},{Index}"
End Function
End Class
Sub Main()
Dim myList As New List(Of String) From {"207.5,1", "373,2", "278.5,3", "134,4", "277,5", "674,7", "58.5,9"}
Dim myData = (myList.Select(Function(d) New Datum(d))).ToList()
Dim dataDescending = myData.OrderByDescending(Function(d) d.Number).ToList()
Console.WriteLine(String.Join(vbCrLf, dataDescending))
Console.ReadLine()
End Sub
End Module
输出:
674,7
373,2
278.5,3
277,5
207.5,1
134,4
58.5,9