我迈出了第一步c#& asp.net,我很享受。 现在,我有一个问题...... 在C#中有一个函数来调用php中的类/方法吗? 例如:
$class = array(
"foo", // class name
"bar" // method name
);
$params = array(
"one",
"two"
);
call_user_func_array($class, $params); //execute Foo->bar("one","two");
答案 0 :(得分:3)
不,没有内置的东西可以做到这一点。您可以构建一个使用反射执行类似操作的方法,但它似乎是一个寻找问题的解决方案。
void Main()
{
CallUserFuncArray("UserQuery+Foo", "Bar", "One", "Two");
}
// Define other methods and classes here
public class Foo
{
public static void Bar(string a, string b){}
}
public void CallUserFuncArray(string className, string methodName, params object[] args)
{
Type.GetType(className).GetMethod(methodName).Invoke(null, args);
}
答案 1 :(得分:2)
正如其他人所说,有多种方法可以模拟这种情况,但C#中没有“烘焙”功能。最灵活的方法是使用反射,但是如果你知道事先要调用的方法列表,你可以用更简单(也更容易处理)的方式来实现。
class Foo
{
public static string FooA(int p1, int p2)
{
return "FooA:" + p1 + p2;
}
public static string FooB(int p1, int p2) { return "FooB:" + p1 + p2; }
public static string FooC(int p1, int p2) { return "FooC:" + p1 + p2; }
}
class Bar
{
//You can use Func<int, int, object> instead of a delegate type,
//but this way is a little easier to read.
public delegate string Del(int p1, int p2);
public static string DoStuff()
{
var classes = new Dictionary<string, Dictionary<string, Del>>();
classes.Add("Foo", new Dictionary<string, Del>());
classes["Foo"].Add("FooA", Foo.FooA);
classes["Foo"].Add("FooB", Foo.FooB);
classes["Foo"].Add("FooC", Foo.FooC);
//...snip...
return classes["Foo"]["FooA"](5, 7);
}
}
如果您不知道您希望以这种方式提供哪种方法,我建议您重新考虑一下您正在尝试做什么。我可以考虑使用字符串来选择执行路径的唯一原因是,如果您计划从用户那里获取这些字符串。如此暴露应用程序的内部细节不仅是一个巨大的禁忌,而且危险地接近eval
类型的功能。 C#没有eval
方法是有原因的,并不是因为设计师忘了把它放进去。
答案 2 :(得分:1)
正如@StriplingWarrior所说,没有内置的等效call_user_func_array
,但你可以用反射做类似的事情。
问题在于,反射代码可以非常快速地变得非常复杂,并且如果你不是非常小心的话,它可能很脆弱且容易出错。
例如,以下功能可以满足您的需求:
public static void CallUserFuncArray(string[] func, params string[] args)
{
var type = Type.GetType(func[0]);
if (type == null)
{
throw new ArgumentException("The specified Class could not be found");
}
var method = type.GetMethod(func[1], BindingFlags.Static | BindingFlags.Public);
if (method== null)
{
throw new ArgumentException("The specified Method could not be found");
}
method.Invoke(null, args);
}
你这样称呼它:
var func = new [] { "Foo", "Bar" };
var args = new [] { "one", "two" };
CallUserFuncArray(func, args);
问题很多。
Bar
是公共静态方法时,代码才有效。 args
数组中的参数不适合目标方法,代码将会爆炸。用卡尔·富兰克林(dotNetRocks成名)来解释:
我遇到了需要解决的问题,所以我使用了Reflection。现在我有两个问题。
我发现你需要做这类事情,然后你可能需要重新思考你的整体设计。