2011-07-31 170 views
1

我有列表。该列表仅保存整数值,但数据类型为字符串。我想根据项目的整数顺序对列表进行排序。字符串列表基于整数的顺序排序

我该如何实现它?

List<string> newZipCodesList = new List<string>(); 
+0

如果它包含整数,为什么不使用'List '? –

+0

我从另一种方法得到它。我无法改变它。 – Lijo

+0

缺省的字符串排序也可以正常工作,而不必将每个字符串转换为int和后面的开销。它效率更高,代码更少。 – user807566

回答

2

您可以使用IComparer接口来实现自己的排序。你将不得不创建一个类来实现T的IComparer,其中T在这种情况下将是字符串。

newZipCodesList.Sort(new Test()); 

    public class Test : IComparer<string> 
    { 
     public int Compare(string x, string y) 
     { 
      //return 1 when first is greater than second 
      if(Convert.ToInt32(x) > Convert.ToInt32(y)) 
       return 1; 
      //return -1 when first is less than second 
      else if (Convert.ToInt32(x) < Convert.ToInt32(y)) 
       return -1; 
      //return 0 if they are equal 
      else 
       return 0; 
     } 
    } 
+1

@Haris你可以通过用一行代替'Compare'方法内部的主体来改善它'return Convert.ToInt32(x) - Convert.ToInt32(Y );';) –

+0

@Jalal:这段代码并不是关于性能,而是关于以最简单的形式教给别人什么东西 –

+0

@Jalal在zipcode的情况下,这种改变将起作用,但在一般情况下,并非如此,与非常小的值相比,非常大的值会以某种方式产生溢出。 –

0
newZipCodesList.Sort((a,b) => { 
          int a1; 
          int a2; 
          if !(int.TryParse(a,out a1)) return 1; 
          if !(int.TryParse(b,out b1)) return -1; 
          return a1.CompareTo(b1); 

} 
2

这是如果你需要整数订购。

List<string> sortedZipCodes = (from code in newZipCodesList 
           orderby Convert.ToInt32(code) 
           select code).ToList(); 
0

如果字符串都是数字,则可以使用其他答案。如果情况并非如此,那么看看更复杂的排序here

2

我不知道你为什么首先使用List<string>,但不管怎样,你可以将列表复制到int列表中,对其进行排序然后将其复制回字符串,或者通过将每个比较器强制转换为int来排序字符串比较一下,也可以使用API​​来NUMERICS值的字符串进行排序,但在这里你可以使用它的唯一数字:

[DllImport("shlwapi.dll", CharSet = CharSet.Unicode, ExactSpelling = true)] 
private static extern int StrCmpLogicalW(String x, String y); 

这样:

newZipCodesList.Sort(StrCmpLogicalW); 

//测试:

List<string> list = new List<string>(new string[] { "1", "4", "17", "5", "112", "0" }); 

list.Sort(StrCmpLogicalW); 

//results: 0, 1, 4, 5, 17, 112 
+0

你能解释为什么DllImport(“shlwapi.dll”?我认为从“哈里斯哈桑”的作品有效。任何不同的想法? – Lijo

+0

'你能解释为什么DllImport(“shlwapi.dll”?我想从“哈里斯哈桑“作品”@Lijo使用@哈里斯的答案,在你的情况下更简单,我没有添加这个答案作为他的替代品,因为我在他之前发布了我的答案,还要注意我们在这里提供替代品。 –

+0

当然,我很欣赏论坛和你的答案。我只是仔细检查是否有任何差异。 – Lijo

2

如果它是安全的假设,列表中的所有元素是相同的长度(例如邮政编码通常是5个字符),则没有必要进行排序之前调用Int.Parse()Convert.ToInt()上每一个项目。即使它们被表示为字符串,“字母”排序仍然应该将它们按数字顺序排列,因为“0”在“1”出现在“2”之前之前出现...并且比执行所有转换更快。

在这种情况下,这会工作:

List<String> zipCodes = new List<String>(); 
zipCodes.Add("00124"); 
zipCodes.Add("00123"); 
zipCodes.Add("98765"); 
zipCodes.Add("12345"); 
zipCodes.Add("33333"); 
zipCodes.Add("24680"); 

// zipCodes = zipCodes.Select(z => z.PadLeft(5, '0')).ToList(); 
zipCodes.Sort(); 

for(int i = 0; i < zipCodes.Count; i++) 
    Console.WriteLine(zipCodes[i]); 

这里是输出:

0
00124 
12345 
24680 
33333 
98765 

如果他们是不一样的长度,你可以垫他们,视以后如何使用列表。 (请参阅代码中的注释行)。 这会将诸如1之类的东西转换为00001

+0

默认排序不工作..尝试使用以下数据 - zipCodes.Add(“1”); zipCodes.Add(“2”); zipCodes.Add(“10”); – Lijo

+1

@Lijo:我没有意识到你会考虑不同长度的邮政编码。我的解决方案假设每个字符串都具有相同数量的字符。我对可处理5个或更少字符的任何邮政编码的代码进行了更新。不过,这取决于您在应用程序中如何使用列表。 – user807566

+1

@Lijo,如果您的邮政编码值为“1”,我鼓励您查找系统滥用邮政编码的位置。不要将复杂的算法复杂化到其他地方,纠正错误。一个结构合理的邮政编码决不应该是“1”。我的猜测是,在某个地方,该计划将其视为一个数字。尽管由数字组成,但邮政编码从不是数字类型,不应该像一个一样处理。 –