簡體   English   中英

如果type參數是struct或class,則選擇泛型實現

[英]Chose generic implementation if the type parameter is struct or class

我希望通過一個實現來實現我的通用IQueue<T>接口,如果T是結構,則執行一個實現,如果T是類,則執行另一個實現。

interface IQueue<T> { ... }

class StructQueue<T> : IQueue<T> where T : struct { ... }

class RefQueue<T> : IQueue<T> where T : class { ... }

我希望有一個基於T類的工廠方法返回一個或另一個的實例:

static IQueue<T> CreateQueue<T>() {
    if (typeof(T).IsValueType) {
        return new StructQueue<T>();
    }
    return new RefQueue<T>();
}

當然,編譯器指示T應該分別是非可空/可空類型參數。

有沒有辦法將T轉換為結構類(以及類類)以使該方法編譯? 是否可以使用C#進行這種運行時調度?

您可以使用Reflection來執行此操作:

static IQueue<T> CreateQueue<T>()
{
    if (typeof(T).IsValueType)
    {
        return (IQueue<T>)Activator
            .CreateInstance(typeof(StructQueue<>).MakeGenericType(typeof(T)));
    }

    return (IQueue<T>)Activator
        .CreateInstance(typeof(RefQueue<>).MakeGenericType(typeof(T)));
}

此代碼使用Activator.CreateInstance方法在運行時創建隊列。 此方法接受您要創建的對象的類型。

要創建表示泛型類的Type ,此代碼使用MakeGenericType方法從開放泛型類型(如StructQueue<>創建封閉的泛型Type對象。

Yacoub Massad的答案是正確的,但只需稍加修改,您就不需要為每次調用CreateQueue運行MakeGenericType。

下面的代碼每個類型運行一次MakeGenericType,因為每種類型的QueueFactory<T>都存在一個單獨的靜態變量,即QueueFactory<int>.queueType將獲得StructQueue<int> ,而QueueFactory<string>.queueType將獲得RefQueue<int>

public class QueueFactory<T>
{
    static Type queueType = typeof(T).IsValueType ?
         typeof(StructQueue<>).MakeGenericType(typeof(T)) : typeof(RefQueue<>).MakeGenericType(typeof(T));

    public static IQueue<T> CreateQueue()
    {
        return (IQueue<T>)Activator.CreateInstance(queueType);
    }
}

在我的半科學測試中,它在大約十分之一的時間內創建了100萬個實例。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM