2017-02-24 130 views
1

我有一個控制器有3個方法具有相同的方法體。唯一的區別是方法類型。我有一個泛型類型的接口,我正在注入控制器。我正在注入接口,因爲我正在使用IoC(StructureMap)。使用泛型與web api控制器

問題是,控制器方法的返回類型與我的界面中方法的泛型類型不匹配。 (GetStatistics1GetStatistics2

爲了演示目的,我更改了第三種方法(GetStatistics3)。我已經將返回類型從IEnumerable<T>鑄造成IEnumerable<Type3>。代碼編譯,但我不知道這是否是最有效的或雄辯的解決方案。

的代碼如下:

接口:

public interface IStatistics<T> 
{ 
    IEnumerable<T> ExecStatistics_SP(DateTime ? date, 
    int ? xd, string iap, int? statisticsType); 
} 

控制器:

public class StatisticsController : ApiController 
{ 
    private readonly IStatistics<T> _repo; 

    public StatisticsController(IStatistics<T> repo) 
    { 
     _repo = repo; 
    } 

    public IEnumerable<Type1> GetStatistics1(string iap, DateTime date, int? statisticsType, int xd) 
    { 
     return _repo.ExecStatistics_SP(date,xd,iap,statisticsType).AsEnumerable(); 
    } 

    public IEnumerable<Type2> GetStatistics2(string aip, DateTime date, int? statisticsType, int xd) 
    { 
     return = _repo.ExecStatistics_SP(date, xd, iap, statisticsType).AsEnumerable(); 
    } 

    public IEnumerable<Type3> GetStatistics3(string iap, DateTime date, int? statisticsType, int xd) 
    { 
     returnValue = _repo.ExecStatistics_SP(date,xd,iap,statisticsType).AsEnumerable(); 
     return (IEnumerable<Type3>) returnValue; 
    } 
} 

回答

1

TL; DR我懷疑這可能是在網絡API;您可能最好爲不同的類創建單獨的控制器。

代碼本身的問題在於類的定義。 StatisticsController不知道T是什麼,這意味着編譯器無法檢查ExecStatistics_SP是否返回兼容類型。

此外,由於IStatistics<T>注入類,沒有辦法區分什麼T是每個方法中,除非你反映過來T每個呼叫。

解決這個問題的另一種方法是讓語言處理所有事情並簡化過程中的類。有了這個解決方案,StatisticsController的調用者知道什麼是T,在您的示例中它是Type1,Type2Type3。實際上,T可以是實現IStatistics<T>的任何類。

public class StatisticsController<T> 
{ 
    private readonly IStatistics<T> _repo; 

    public StatisticsController(IStatistics<T> repo) 
    { 
     _repo = repo; 
    } 

    public IEnumerable<T> GetStatistics(string iap, DateTime date, int? statisticsType, int xd) 
    { 
     return _repo.ExecStatistics_SP(date, xd, iap, statisticsType); 
    } 
} 

我不知道你的DI框架的Web API的情況下如何處理這一點,但誰調用GetStatistics必須用一個類型實現IStatistics<T>已經實例化StatisticsController。在自己的代碼使用將如下所示:

var repo = new StatisticsRepo<Type1>(); // Made-up repo class 
var controller = new StatisticsController<Type1>(repo); 
IEnumerable<Type1> values = controller.GetStatistics(...); 
// etc 
+0

附註:我本來試圖用[協方差(https://msdn.microsoft.com/en-us/library/dd799517(V解決這個= vs.110).aspx),但我無法弄清楚。 – Scott

+0

謝謝Scott。我會檢查出來的。 – user1647160