返回key的最小值作为集合的属性

时间:2017-02-15 17:15:52

标签: c#

我已经定义了一个名为Diversion的新类,它继承自Dictionary,用于保存一组DateTime键和相关的int值。

我想将最早的键值和平均int值作为类的属性返回(假设它已被填充)。

是否有更有效的方法来迭代字典?在我定义类时,如何引用类的实例?

提前感谢您的帮助!

   public class Diversion : Dictionary<DateTime, int>
{
    private DateTime _starttime;
    private decimal _avg;

    public DateTime Starttime {
        get {
            if (Diversion.count > 0) {
                _starttime = new DateTime(2999,1,1);
                foreach(KeyValuePair<DateTime, int> de in Diversion) {
                    if (de.key < _starttime) _starttime = de.key;
                }
                return _starttime;
            }
            else    return; 
         }
    }

    public DateTime AvgVal {
        get {
            if (Diversion.count > 0) {
                _avg = 0;
                foreach(KeyValuePair<DateTime, int> de in Diversion) {
                    _avg = _avg + de.value;
                }
                _avg = _avg / Diversion.count;
                return _avg;
            }
            else    return; 
         }
    }       

    public Diversion() {}
}

2 个答案:

答案 0 :(得分:1)

是。您可以使用LINQ来隐藏您的复杂性 Dictionary.Keys
Enumerable.Min Enumerable.Average

public DateTime Starttime 
{
    get 
     {
        if (this.Count > 0) 
        {
             return this.Keys.Min();    
        }
        return new DateTime(2999,1,1);;
     }
}

public DateTime AvgVal 
{
    get
    {
        if (this.Count > 0) 
           return this.Values.Average();  
        else    
           return DateTime.MinValue; //something must be returned.
   }
}

扩展任何类(在本例中为Dictionary)时,可以使用this关键字访问基类(和当前类)的所有属性。在您的代码中,您使用的是基类名称,这是不正确的。

答案 1 :(得分:0)

您可以实现 Dictionary<TK,TV>包装实际字典,而不是继承 IDictionary<TK,TV>。这样您就可以控制对包装字典的访问,保持当前的最小值和总数:

public class Diversion : IDictionary<DateTime,int> {
    private decimal currentTotal;
    private SortedSet<DateTime> keys = new SortedSet<DateTime>();
    private Dictionary<DateTime,int> dict = new Dictionary<DateTime,int>();
    ...
    public decimal AvgVal {
        get {
            if (dict.Count == 0) throw InvalidOperationException();
            return currentTotal / dict.Count;
        }
    }
    public DateTime StartTime {
        get {
            if (dict.Count == 0) throw InvalidOperationException();
            return keys.Min;
        }
    }
}

您将通过将调用转发给已包装的IDictionary<DateTime,int>来实现dict的所有方法,但有三个例外:

  • 添加新条目的操作需要将密钥添加到keys并按currentTotal增加value
  • 按键删除条目的操作需要删除密钥并减少currentTotal
  • 替换特定密钥中的条目的操作需要从currentTotal中减去旧值,并将新值添加到结果中。

这将使您的其他操作AvgValStartTime即时完成,无论集合的当前大小如何。另一方面,实现需要维护一个平衡的键树,因此所有的变异操作都将变为O(log 2 n)。