2012-04-16 4 views
7

Func<>型の引数を動的に設定する方法はありませんので、無限のif文を使用する必要はありませんか?動的にFunc <>型を設定する

Type t = Type.GetType("System.Decimal"); 
Func<t> foo = new Func<t>(some_function); 

の代わりに::

Func<Decimal> foo = new Func<Decimal>(some_function); 

UPDATE:のような

何か

は、ここに私のコードからの抜粋です:

Type t = typeof(StavkaDokumenta).GetProperty(pd.Polje).PropertyType; 
ParameterExpression pe = Expression.Parameter(typeof(StavkaDokumenta), "stavka"); 
Expression expr = Expressions.ResolveCompleteExpression(pe, pd.Expression); 
Expression final = Expression.Convert(expr, t); 
if (t == typeof(decimal)) 
{ 
    var lambda = Expression.Lambda<Func<StavkaDokumenta, decimal>>(final, pe); 
    o = lambda.Compile().Invoke(stavka); 
} 
if (t == typeof(decimal?)) 
{ 
    var lambda = Expression.Lambda<Func<StavkaDokumenta, decimal?>>(final, pe); 
    o = lambda.Compile().Invoke(stavka); 
} 
else if (t == typeof(int)) 
{ 
    var lambda = Expression.Lambda<Func<StavkaDokumenta, int>>(final, pe); 
    o = lambda.Compile().Invoke(stavka); 
} 
else if (t == typeof(int?)) 
{ 
    var lambda = Expression.Lambda<Func<StavkaDokumenta, int?>>(final, pe); 
    o = lambda.Compile().Invoke(stavka); 
} 
else if (t == typeof(string)) 
{ 
    var lambda = Expression.Lambda<Func<string>>(final, null); 
    o = lambda.Compile().Invoke(); 
} 

pd.Poljeは文字列です - プロパティインの名前ide "StavkaDokumenta"クラス。 pd.Expressionは、Poljeの型に評価される文字列式です。 stavkaはStavkaDokumentaのインスタンスです。

+4

あなたが無限のifを使用しているなら、あなたの現在のアプローチについて改善の余地がありますか?私は少なくともそれを検討するだろう。 – Botz3000

+3

あなたが解決しようとしている無限のifチェーンの例を教えてください。 – GregC

+3

あなたが無限の 'xxx is SomeType'を使用しているなら、おそらくあなたのデザインに何か間違いがあります。 –

答えて

9

今、あなたはあなたが本当に欲しいものを示したことが、答えははるかに簡単です: あなたはその式の戻り値で明らかにのみ関心があるとして、あなたはこのようにコードを変更することができます:

Type t = typeof(StavkaDokumenta).GetProperty(pd.Polje).PropertyType; 
ParameterExpression pe = Expression.Parameter(typeof(StavkaDokumenta), "stavka"); 
Expression expr = Expressions.ResolveCompleteExpression(pe, pd.Expression); 
Expression final = Expression.Convert(expr, t); 

if (t == typeof(string)) 
{ 
    var lambda = Expression.Lambda<Func<string>>(final, null); 
    o = lambda.Compile().Invoke(); 
} 
else 
{ 
    var lambda = Expression.Lambda(final, pe); 
    o = lambda.Compile().DynamicInvoke(stavka); 
} 

旧答え:

あなたがこれを達成するためにFunc<T>にジェネリック医薬品と暗黙的な変換を使用することができます。

Func<T> GetFunc<T>(Func<T> func) 
{ 
    return func; 
} 

ので、同様の方法グループでそれを呼び出します。

decimal SomeMethod() 
{ 
    // ... 
} 

fooはタイプFunc<decimal>のものであろう:

var foo = GetFunc(SomeMethod); 

をこれはSomeMethodはこのようになっていることを前提としています。返品タイプSomeMethodstringである場合、fooのタイプはFunc<string>となります。このコードでは何が起こる


は以下の通りです:

GetFuncに渡されたパラメータは、いわゆる「メソッド・グループ」とないタイプFunc<T>の変数です。まさにここで何が起こっている暗黙的な変換がされ

Func<decimal> func = SomeMethod; // an implicit conversion happens here 

こと:GetFunc前にも呼ばれ、メソッドグループSomeMethodは変数の変換されたが、Func<T>の変数にメソッドグループからの暗黙の変換が存在しますタイプFunc<T>Tで使用される具体的な型は、メソッドSomeMethod()の戻り型に基づいてコンパイラによってさらに推測されます。
私たちの目標は、私たちのメソッドグループに基づいてFunc<T>のインスタンスを作成することでした。また、メソッドが呼び出される前にパラメータの変換がすでに行われているため、作成したインスタンスをメソッドから返すだけです。

+0

申し訳ありませんが、私は従いません。あなたのメソッド 'GetFunc 'は事実上何もしません。このパラメータは、開始したのと同じ型としてパラメータを返します。 – Yuck

+0

@Yuck:メソッドグループ( 'SomeMethod')から' Func '型の変数への暗黙的な変換が存在するため、呼び出し自体に魔法が発生しています。 –

+0

私はダニエルに今それを試してみるだろうが、それはトリックをするだろうと思う。私は立ち往生し、ifsで解決しようとしていた... –

関連する問題