0

我正在实现一个扩展方法,TKeyIDictionary<TKey, TValue>作为参数返回。如果TValuedouble,则该方法可能会返回TKey具有最高值的 a。否则,它将随机返回一个TKey.

    public static TKey Sample<TKey>(this IDictionary<TKey, double> probabilityTable, Random r)
    {
        probabilityTable.Normalize();

        var roll = r.NextDouble();
        var temp = 0.0;
        foreach (var key in probabilityTable.Keys)
        {
            temp += probabilityTable[key];
            if (roll <= temp)
                return key;
        }

        return default(TKey);
    }

    public static TKey Sample<TKey, TValue>(this IDictionary<TKey, TValue> dictionary, Random r)
    {
        return dictionary.Skip(r.Next(dictionary.Count)).FirstOrDefault().Key;
    }

    public static IDictionary<TKey, double> Normalize<TKey>(this IDictionary<TKey, double> probabilityTable)
    {
        if (probabilityTable.Any(x => x.Value < 0))
            throw new ArgumentOutOfRangeException("probabilityTable", "Probability is expected to be positive.");

        var sum = probabilityTable.Sum(x => x.Value);

        if (Math.Abs(sum - 1) > 1e-8)
            return probabilityTable.ToDictionary(x => x.Key, x => x.Value / sum);

        if (Math.Abs(sum) < 1e-8)
            return probabilityTable.ToDictionary(x => x.Key, x => 1.0 / probabilityTable.Count);

        return probabilityTable;
    }

问题是即使使用ofSample<TKey, TValue>也总是调用它。我可以用 where 子句指定类型exclude double 的任何方式吗?IEdoubleTValueTValuewhere TValue: !double

调用扩展函数的代码如下:

        var r = new Random();
        var pt = new Dictionary<char, double> {{'A', 0.1}, {'B', 0.2}, {'C', 0.7}};
        var ct = new Dictionary<char, char> {{'A', 'D'}, {'B','E'}, {'C', 'F'}};
        Console.WriteLine(pt.Sample(r)); // expected to return 'C' mostly but uniformly returns key
        Console.WriteLine(ct.Sample(r));
4

1 回答 1

0

约束不是签名的一部分,也许以下链接可以帮助您:

http://blogs.msdn.com/b/ericlippert/archive/2009/12/10/constraints-are-not-part-of-the-signature.aspx

于 2012-10-01T15:59:35.090 回答