【问题标题】:Most efficient way to compare a string integer against a range within C# [closed]将字符串整数与 C# 中的范围进行比较的最有效方法 [关闭]
【发布时间】:2020-11-04 02:45:18
【问题描述】:

我需要检查一个整数范围,但我用于比较的字段是一个字符串。

此字符串中可能包含非整数值。应该跳过具有非整数值的字符串。

范围只是另外两个整数。

如果字符串列表中有一万个数字,我想知道最快的方法是什么。我考虑过简单的 int.TryParse,然后在范围之间进行条件检查,但我想知道是否有更快的方法来做到这一点

不寻求意见,热衷于查看基准数据。

以下是数据和范围最小值/最大值的示例。

int min = 1000;
int max = 4999;

List<string> orderNumbers = new List<string>
{
    "4021",
    "*1002",
    "5000",
    "4500"
};

【问题讨论】:

    标签: c# performance integer string-comparison


    【解决方案1】:

    TryParse 会很好用

    var results = orderNumbers
         .Select(x => int.TryParse(x, out var i) ? i : (int?) null)
         .Where(x => x >= min && x <= max)
         .Cast<int>() // resolve the nullable;
    

    注意:您可以轻松使用.Select(x =&gt; x.Value),它必须创建完全相同的IL


    如果您经常这样做,那么理想情况下,您的列表不会是 string 类型。

    或者只使用foreach 循环

    var results = new List<int>(orderNumbers.Count);
    foreach (var item in orderNumbers)
       if (int.TryParse(item, out var value) && value >= min && value <= max)
          results.Add(value);
    

    如果你觉得无聊,创建你自己的迭代器扩展方法

    public IEnumerable<int> GetRange(this IEnumerable<string> source, int min, int max)
    {
       foreach (var item in source)
          if (int.TryParse(item, out var value) && value >= min && value <= max)
             yield return value;
    }
    

    用法

    var results = orderNumbers.GetRange(min,max);
    

    如果您正在查看原始效率,并且您的有效数字始终只是没有文化差异的数字,例如 1000 的分隔符等。您可以通过自己的 TryParse 方法和(可选)使用指针或 Span&lt;T&gt; 迭代字符来获得更好的性能@

    [MethodImpl(MethodImplOptions.AggressiveInlining)]
    public static unsafe bool MyTryParse(string source, int min, int max, out int value)
    {
       value = 0;
       fixed (char* p = source)
       {
          for (var i = 0; i < source.Length; i++)
             if (p[i] >= '0' && p[i] <= '9') 
                value = value * 10 + p[i] - '0';
             else 
                return false;
       }
       return value >= min && value <= max;
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-08-10
      • 1970-01-01
      相关资源
      最近更新 更多