2010-03-16 76 views
1

比方說,我有一個類型:如何創建一個採用T或IEnumerable的泛型類型<T>?

public class Transformer<T, TResult> 
    where T : IMessage 
    where TResult : IMessage 
{ 
    private Func<T, IEnumerable<TResult>> _transformer; 

    public Transformer(Func<T, TResult> transformer) 
    { 
     _transformer = null // ? 
    } 

    public Transformer(Func<T, IEnumerable<TResult>> transformer) 
    { 
     _transformer = transformer; 
    } 
} 

所以在本質上,我想Func<T, TResult>轉換成Func<T, IEnumerable<TResult>>在第一個構造函數。

我試圖創建一個私有的內部類,它Func<T, TResult>和定義返回IEnumerable的這樣一個方法:

private class TransformerWrapper 
{ 
    private readonly Func<T, TResult> _func; 

    public TransformerWrapper(Func<T, TResult> func) 
    { 
     _func = func; 
    } 

    public IEnumerable<TResult> Transform<T>(T message) where T : IMessage 
    { 
     yield return _func(message); 
    } 
} 

但它不是真正的工作了。我得到一個錯誤,說代表有一個無效的參數 - 不能轉換從T到T.

首先,編譯器錯誤發生了什麼,第二,有沒有另一種方式?

更新

分鐘,我張貼後,我發現了一個解決方案:

public Transformer(Func<T, TResult> transformer) 
{ 
    _transformer = new TransformerWrapper<T, TResult>(transformer).Transform; 
} 

而且,

private class TransformerWrapper<T, TResult> 
{ 
    private readonly Func<T, TResult> _func; 

    public TransformerWrapper(Func<T, TResult> func) 
    { 
     _func = func; 
    } 

    public IEnumerable<TResult> Transform(T message) 
    { 
     yield return _func(message); 
    } 
} 

我仍然無法得到解決,爲什麼第一個解決方案我的頭不工作。我需要考慮那個...

回答

1

試試這個:

public Transformer(Func<T, TResult> transformer) 
{ 
    _transformer = t => Convert(t, transformer); 
} 

private static IEnumerable<TResult> Convert(T value, Func<T, TResult> transformer) 
{ 
    yield return transformer(t); 
} 
+0

謝謝!我喜歡這種方法,因爲我不需要創建一個包裝類。 – 2010-03-16 15:34:31

1

您在Transform<T>函數中指定了一個新的通用類型T。由於TTResult已在父類中定義,因此子類中的任何內容都不需要是通用的。

從方法簽名中刪除<T>和通用限定符,它應該進行編譯。

public IEnumerable<TResult> Transform(T message) 
{ 
    yield return _func(message); 
} 
1

您的內部類更改爲:

private class TransformerWrapper 
    { 
     private readonly Func<T, TResult> _func; 

     public TransformerWrapper(Func<T, TResult> func) 
     { 
      _func = func; 
     } 

     public IEnumerable<TResult> Transform(T message) 
     { 
      yield return _func(message); 
     } 
    } 
} 

編譯已經知道T是什麼,你不需要再限制的方法。

相關問題