我在C#3.5中有两个方法,它们是相同的一个函数调用, 在下面的代码段中,请参阅clientController.GetClientUsername vs clientController.GetClientGraphicalUsername
private static bool TryGetLogonUserIdByUsername(IGetClientUsername clientController, string sClientId, out int? logonUserId)
{
string username;
if (clientController.GetClientUsername(sClientId, out username))
{
// ... snip common code ...
}
return false;
}
private static bool TryGetLogonUserIdByGraphicalUsername(IGetClientUsername clientController, string sClientId, out int? logonUserId)
{
string username;
if (clientController.GetClientGraphicalUsername(sClientId, out username))
{
// ... snip common code ...
}
return false;
}
有没有办法(委托,lamda的?)我可以传递给我想调用的clientController上的哪个方法?
谢谢!
答案 0 :(得分:9)
虽然您可以将委托作为参数传递,但我建议使用不同的路径。封装if
语句的主体,该语句涉及另一个函数中的公共代码,并在两个函数中调用该函数。
Visual Studio在上下文菜单中有一个“重构->
提取方法”功能。您只需填写其中一个实体,选择实体并使用该功能自动提取其中的方法。
答案 1 :(得分:7)
不确定。只需像这样定义一个委托:
public delegate bool GetUsername(string clientID, out string username);
然后将其传递给您的函数并调用它:
private static bool TryGetLogonUserId(IGetClientUsername clientController, string sClientId, out int? logonUserId, GetUsername func)
{
string username;
if (func.Invoke(sClientId, out username))
{
// ... snip common code ...
}
return false;
}
要使用委托调用该函数,您将执行以下操作:
TryGetLogonUserId(/* first params... */, clientController.GetClientUsername);
答案 2 :(得分:1)
函数的类型写为Func< inParam1,inParam2,...,returnParam>。我不确定“out”参数是否在“Func”类型中正确传递,但你应该能够使你的功能像
void TryGetLogon(Func<IGetClientUsername, string, out int?, bool> f) {
// ...
f(x, y, z, a);
}
// ...
TryGetLogon(TryGetLogonUserIdByGraphicalUsername);
答案 3 :(得分:0)
您可以传递MethodInfo,可以静态查找。但是,我同意可能需要重新设计。
private static readonly MethodInfo getRegularLogin = typeof(IGetClientUsername).GetMethod("GetClientUsername");
private static bool TryGetLogonUserIdByUsername(IGetClientUsername clientController, string sClientId, out int? logonUserId)
{
string username;
return TryGetLoginReflective(getRegularLogin, clientController, sClientId, out username, out logonUserId);
}
private static readonly MethodInfo getGraphicalLogin = typeof(IGetClientUsername).GetMethod("GetClientGraphicalUsername");
private static bool TryGetLogonUserIdByGraphicalUsername(IGetClientUsername clientController, string sClientId, out int? logonUserId)
{
string username;
return TryGetLoginReflective(getGraphicalLogin, clientController, sClientId, out username, out logonUserId);
}
private static bool TryGetLoginReflective(MethodInfo method, IGetClientUsername clientController, string sClientId, out string username, out int? logonUserId)
{
object[] args = new object[]{sClientId, null};
if((bool)method.Invoke(clientController, args))
{
// ... snip common code ...
}
logonUserId = ...;
username = (string)args[1];
return false;
}
答案 4 :(得分:0)
如何简单地传入一个布尔标志?
private static bool TryGetLogonUserIdByUsername(
IGetClientUsername clientController,
string sClientId, out int? logonUserId, bool graphical)
{
string username;
bool gotClient = false;
if (graphical)
{
gotClient = clientController.GetClientGraphicalUsername(
sClientId, out username);
}
else
{
gotClient = clientController.GetClientUsername(
sClientId, out username);
}
if (gotClient)
{
// ... snip common code ...
}
return false;
}