【问题标题】:Is the method that I am using for retrieval in my generic list optimized我在通用列表中用于检索的方法是否已优化
【发布时间】:2010-06-06 22:16:13
【问题描述】:

在某个时候会有大量的记录,大约 50,000 条。 考虑到这一点,GetEquipmentRecord 方法可以完成任务。 谢谢你的意见。

c# ,net 2,0

public enum EquipShift { day, night };

public class EquipStatusList : List<EquipStatus>
{
    string SerialFormat = "yyyyMMdd";

    int _EquipmentID;
    string _DateSerial;
    EquipShift _Shift;

    public EquipStatus GetEquipmentRecord(int equipmentID, EquipShift shift, 
                                            DateTime date)
    {
        _DateSerial = date.ToString(SerialFormat);
        _Shift = shift;
        _EquipmentID = equipmentID;

        return this.Find(checkforEquipRecord);
    }

    bool checkforEquipRecord(EquipStatus equip)
    {
        if ((equip.EquipmentID == _EquipmentID)
              && (equip.Shift == _Shift) 
              && (equip.Date.ToString(SerialFormat) == _DateSerial))
            return true;
        else
            return false;
    }
}

更新: 我已将评估更改为阅读

           if ((equip.Date.Date == _date.Date) &&  (equip.EquipmentID == _EquipmentID) && (equip.Shift == _Shift)  )

不确定是否有帮助

【问题讨论】:

    标签: c# .net-2.0


    【解决方案1】:

    无需评论您选择的算法,我们可以说它可能已经足够优化了

    你有一个 O(n) find() 在那里;例如,使用二进制搜索搜索排序列表将是 O(lg n),搜索 hash-set(或 C# 2.0 中的 Dictionary)将是 O(1)。如果你经常调用这个函数,Hash-set 显然是最好的选择。

    瓶颈很少出现在您预期的地方,因此您在此特定实例上提出问题意味着,总的来说,稍后进行分析实际上会表明大幅放缓在其他地方。

    【讨论】:

    • 感谢您的评论...我希望代码先评估一个日期,然后如果不在范围内,则保释。作为新手,我几乎一直处于未知领域。
    【解决方案2】:

    您可以通过实现合适的GetHashCode 方法并使用System.Collections.Generic.HashSet&lt;EquipStatus&gt; 作为后备容器来大大加快这一速度。但是,由于尚不完全清楚您是如何使用您的课程的(即您使用了哪些其他 List&lt;T&gt; 方法),ymmv。

    【讨论】:

    • 了解详细说明该方法的任何可用资源
    • 嗯。您使用的是 .net 2.0 吗?如果是这样 HashSet 不可用。但是,如果少量的额外存储不是问题,您始终可以使用 Dictionary 的键。这个问题概述了GetHashCode的来龙去脉...stackoverflow.com/questions/1378686/…
    【解决方案3】:

    不,不是。您的整个构造无法在多任务环境中使用。您正在存储要搜索的详细信息作为类的实例成员。我会利用 PLINQ(Parallel Linq)和通常的运算符,我也不会从 List 本身派生,而是提供这样的扩展方法:

    public static EquipStatus GetEquipmentRecord(this IEnumerable<EquipStatus> list, int equipmentID, EquipShift shift, DateTime date)
    {
      return list.AsParallel().FirstOrDefault(e => e.EquipmentID == equipmentID && e.Shift == shift, e.Date.Date == date.Date);
    }
    

    这样,可以同时进行多个搜索。

    【讨论】:

    • 在 .net 2.0 中是否可用
    • 好的,您的问题并不清楚。可悲的是,这至少是 .net3.5 和 c#3。我重新整理了您的问题,以便更清晰可见。
    【解决方案4】:

    改善checkForEquipRecord 方法的一个明显方法是改变

    if ((equip.Date.Date == _date.Date) &&  (equip.EquipmentID == _EquipmentID) && (equip.Shift == _Shift)  )
        return true;
    else
        return false;
    

    只给return (equip.Date.Date == _date.Date) &amp;&amp; (equip.EquipmentID == _EquipmentID) &amp;&amp; (equip.Shift == _Shift)

    就效率而言,它可能已经是 JIT 编译器所做的优化。

    【讨论】:

    • 啊,是的!...我们会期望得到丰厚的回报吗?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-15
    • 1970-01-01
    • 2013-07-05
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多