簡體   English   中英

C#接口中如何返回Type T?

[英]How to return Type T in interface in C#?

我有一個這樣的界面:

public interface IUser{
    //some properties here

    T ToDerived(User u);
}

我是界面開發的新手,所以這就是我想要完成的。 我將有一個基地 class

public class User 

不實現上述接口。 然后我將有一個派生 class

SalesUser : User, IUser
{
    //no properties needed because they exist in the User class

    SalesUser ToDerived(User u)
    {
        //code for converting a base User to a derived SalesUser
    }
}

我想在 SalesUser class 中為 ToDerived(User u) 編寫 function,但在界面中,我不知道如何定義它,因為我現在在界面中的 ToDerived 方法聲明未編譯。

我希望這是有道理的。

public interface IUser<T> where T : User
{
    //some properties here

    T ToDerived(User u);
}

SalesUser : User, IUser<SalesUser>
{
    //no properties needed because they exist in the User class

    SalesUser ToDerived(User u)
    {
        //code for converting a base User to a derived SalesUser
    }
}

不確定這是你想要的,但我在接口上添加了泛型類型約束,以確保泛型類型是User或繼承自它。

Oded 的答案解決了編譯問題,允許您定義滿足接口的 ToDerived 方法。 但是,正如我在評論中所說,我不確定這是最好的實現方式。

我遇到的主要問題是在 static 上下文中通常需要像這樣的轉換方法。 您沒有 SalesUser 的實例; 您想要一個,並且有一個用戶,因此您在 static 上下文 ( SalesUser.ToDerived(myUser) ) 中調用該方法並獲得一個 SalesUser(該方法更恰當地命名為 FromUser() 或類似名稱)。 您在界面中指定的方法要求您已經有一個 SalesUser,以便將 User 轉換為 SalesUser。 我能想到的唯一真正需要預先存在的 SalesUser 的情況是“部分克隆”; 您正在使用傳入的 User 和調用方法的 SalesUser 的信息創建一個新的 SalesUser 實例。 在所有其他情況下,您要么不需要 SalesUser(轉換,如前所述應該為 static),要么不需要 User(生成新實例的“克隆”或“深度復制”方法與調用該方法的實例相同的數據)。

此外,您的 class 的消費者必須知道他們必須調用 ToDerived() 才能執行從 User 到 SalesUser 的轉換。 通常,C# 程序員會期望顯式或隱式轉換可用:

public class SalesUser
{

    public static explicit operator (User user)
    {
        //perform conversion of User to SalesUser
    }

}

//the above operator permits the following:
mySalesUser = (SalesUser)myUser;

... 或者,如果轉換運算符失敗,人們希望能夠使用用戶構造一個 SalesUser:

public class SalesUser:IUser
{
   public SalesUser(User user)
   {
      //initialize this instance using the User object
   }
}

//the above allows you to do this:
mySalesUser = new SalesUser(myUser);

//and it also allows the definition of a method like this,
//which requires the generic to be an IUser and also requires a constructor with a User
public void DoSomethingWithIUser<T>(User myUser) where T:IUser, new(User)
{ 
    //...which would allow you to perform the "conversion" by creating a T:
    var myT = new T(myUser);
}

現在,static個成員不滿足接口定義,接口不能定義static個成員或構造函數簽名。 這告訴我 IUser 接口不應該嘗試定義轉換方法; 相反,需要某種 IUser 的方法可以簡單地指定它,並且用戶可以根據需要提供實現,而無需實現知道它可以轉換為自身。

記住一個接口定義了一個 class 和它的成員沒有提供任何實現,你可以創建一個接口但是接口必須有實現 class。

暫無
暫無

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

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