我需要添加任何返回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);
}
}
答案 0 :(得分: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
,则可能会失败。(不多也不少)。
我仍然觉得整体而言,无论你做什么,都会受益于不同的设计。
答案 1 :(得分:0)
定义一个新的类对象,它具有您需要的委托和参数列表,然后dictionary<string, clsObject>
将是您定义字典的方式。
答案 2 :(得分:0)
将该方法添加到集合中时,将该方法强制转换为Func<T1, T2, .., TResult>
:
Program.AddFunction(
(Func<double, double, double, double, double, double, double>)MyFunc);
答案 3 :(得分:0)
你的意思是defining a delegate with the params
modifier on its arguments吗?答案显然是否定的,因为编译器会在方法调用中将其他参数转换为数组,但对于委托则不会。请参阅链接以获取一些解决方案。
答案 4 :(得分:0)
你需要将你的委托声明为返回一个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();
}
}