何时在没有约束的情况下在c#中使用泛型方法?

时间:2013-03-10 21:04:17

标签: c#

为什么你想在c#中使用泛型方法而不至少对参数设置一些约束?我真的不能想到一个可以传递任何有用的方法,可以传递任何类型。

3 个答案:

答案 0 :(得分:5)

每当您使用它时,例如IEnumerable<T>扩展方法。

答案 1 :(得分:5)

一个简单的例子:

void Swap<T>(ref T a, ref T b)
{
    T temp = a;
    a = b;
    b = temp;
}

不要忘记每个类型T派生自System.Object,因此继承了一些有用的方法。嗯,严格说不是每种类型。例如,接口不会从object继承,但实现它们的类型会继承。因此,即使T是接口类型,C#也允许您访问从object继承的成员。

答案 2 :(得分:1)

当你需要这个方法时......通用。

我有一个例子,我在另一个答案中发布了。这是一个名为ExecuteTimedAction的方法。它需要一个动作,几个参数,动作的次数,执行它,并返回结果。它在公共库中用于记录执行时间所需的任何内容。

此方法不关心类型T.它只执行另一个方法(委托)并返回该方法的返回类型的任何类型。不需要约束,因为在需要约束的方法中没有依赖。

我认为这是一个很好的候选人,当然不是唯一的例子,而是一个最重要的例子。这是方法,来自this回答:

    /// <summary>
    /// Generic method for performing an operation and tracking the time it takes to complete (returns a value)
    /// </summary>
    /// <typeparam name="T">Generic parameter which can be any Type</typeparam>
    /// <param name="actionText">Title for the log entry</param>
    /// <param name="func">The action (delegate method) to execute</param>
    /// <returns>The generic Type returned from the operation's execution</returns>

    public static T ExecuteTimedAction<T>(string actionText, Func<T> executeFunc, Action<string> logAction)
    {
        string beginText = string.Format("Begin Execute Timed Action: {0}", actionText);

        if (null != logAction)
        {
            logAction(beginText);
        }
        else
        {
            LogUtil.Log(beginText);
        }

        Stopwatch stopWatch = Stopwatch.StartNew();
        T t = executeFunc(); // Execute the action
        stopWatch.Stop();

        string endText = string.Format("End Execute Timed Action: {0}", actionText);
        string durationText = string.Format("Total Execution Time (for {0}): {1}", actionText, stopWatch.Elapsed);

        if (null != logAction)
        {
            logAction(endText);
            logAction(durationText);                
        }
        else
        {
            LogUtil.Log(endText);
            LogUtil.Log(durationText);
        }

        return t;
    }