0

double を返し、任意の量の double パラメーターを取得する任意のメソッドを Dictionary に追加できるようにする必要があります。お願い助けて。

class Program
{
Dictionary<string, Delegate> _functions;
static double MyFunc (double x, double y, double z, double q, double r, double t)
    {
        return 100;
    }
// and the user can create his functions with any amount of parameters
static void AddFunction (Delegate d)
    {            
        _functions.Add (d.Method.Name, d);
    } 
static void Main (string [] args)
    {
        _functions = new Dictionary<string, Delegate> ();
        Program.AddFunction(MyFunc);
    }
} 
4

5 に答える 5

1

ええと、これを正確にどのように呼び出すつもりなのかわかりません。可変数の入力があるため、それらを配列入力のように扱うことができます。

delegate double MyDictionaryDelegate(params double[] input);

static Dictionary<string, MyDictionaryDelegate> _functions;

static void AddFunction (MyDictionaryDelegate d)
{            
   _functions.Add(d.Method.Name, d);
} 

しかし、これは本質的に、呼び出された関数をコレクションの処理に変えます (これが意味する利点/制限のいずれかを伴います):

public static double MyFunc (params double[] input)
{
   return input.Sum();
}

したがって、使用法は次のようになります。

_functions = new Dictionary<string, MyDictionaryDelegate> ();
AddFunction(MyFunc);
Console.WriteLine(_functions["MyFunc"](1, 2.5, 0));//3.5

しかし、次のようなリストではなく、パラメーター引数の元のリストを保持したいのではないかと思います。

public static double AnotherFunc(double x, double y, double z)
{
    return x + y + z;
}

単純にラッパー関数を使用できます。

public static double AnotherFunc(params double[] input)
{
    //preferably with some check that the proper number of 
    //input parameters are included
    return AnotherFuncImpl(input[0], input[1], input[2]);
}

しかし、これは私にとって全体的に危険に思えます。私はそれをお勧めするかどうかわかりません。

param double[] input編集:これは、配列を回避し、常に固定パラメーター引数を持つ別のオプションです。をそのまま使用Delegateしますが、その を使用する必要がありますDynamicInvoke。さらに、AddFunction合理的に持つと予想されるパラメーターの数ごとに、いくつかのオーバーロードを宣言します。

static Dictionary<string, Delegate> _functions;

private static void AddFunction (string functionName, Delegate d)
{            
   _functions.Add(functionName, d);
} 

private static void AddFunction(Func<double> d)
{            
   _functions.Add(d.Method.Name, d);
} 

private static void AddFunction(Func<double, double> d)
{            
   _functions.Add(d.Method.Name, d);
} 

private static void AddFunction(Func<double, double, double> d)
{            
   _functions.Add(d.Method.Name, d);
} 

private static void AddFunction(Func<double, double, double, double> d)
{            
   _functions.Add(d.Method.Name, d);
} 

//additional overloads up to N parameters

次に、使用法は次のようになります。

public static double MyFunc(double x, double y, double z)
{
    return x + y + z;
}

_functions = new Dictionary<string, Delegate> ();
AddFunction(MyFunc);
Console.WriteLine(_functions["MyFunc"].DynamicInvoke(1, 2.5, 0));//3.5

しかし、繰り返しになりますが、呼び出し側が必要なパラメーターDynamicInvoke正確な数(それ以上でもそれ以下でもありません) で適切に呼び出さなかった場合、これは失敗する可能性があります。

全体として、あなたがしていることは何でも、別のデザインの恩恵を受けるように感じます.

于 2013-08-29T16:47:53.227 に答える
0

double を返すようにデリゲートを宣言し、double のパラメーターを取得する必要があります。完全に機能する例を次に示します。

public class Widget
{
    // declares a delegate called AddDelegate that takes a param of doubles
    public delegate double AddDelegate(params double[] dbls);
    Dictionary<string, AddDelegate> functions;

    public Widget()
    {
        functions = new Dictionary<string, AddDelegate>();
    }

    public void Add(AddDelegate d)
    {
        functions.Add(d.Method.Name, d);
    }

    public void Run()
    {
        foreach (var kvp in functions)
        {
            // write out the name and result of each function added to our list
            Console.Write(kvp.Key);
            Console.Write(": ");
            Console.Write(kvp.Value(10.0, 10.0, 10.0, 10.0));
        }
    }
}

class Program
{
    static double CalcDouble(params double[] dbls)
    {
        double total = 0.0;
        foreach (double d in dbls)
        {
            total += d;
        }
        return total;
    }


    static void Main(string[] args)
    {
        var w = new Widget();
        w.Add(new Widget.AddDelegate(CalcDouble));
        w.Run();
    }
}
于 2013-08-29T16:48:00.530 に答える
0

必要なデリゲートとパラメーター リストを持つ新しいクラス オブジェクトをdictionary<string, clsObject>定義すると、ディクショナリを定義する方法になります。

于 2013-08-29T16:36:17.293 に答える
0

Func<T1, T2, .., TResult>コレクションに追加するときに、メソッドを としてキャストします。

Program.AddFunction(
    (Func<double, double, double, double, double, double, double>)MyFunc);
于 2013-08-29T16:43:53.850 に答える