我想做这样的事情,但这是不可能的。(无法从' void'转换为' System.Action&#39 ;)
IsAllowed()
我可以发送参数" n",作为" setMethod"中的第二个参数。方法,但我必须在传递给" del.Invoke(PARAM)"之后存储一个变量。我想使用" del.Invoke()"。
答案 0 :(得分:2)
你似乎对代表有误解。代表代表方法,而不是方法调用。如果为方法提供参数,它将成为方法调用。所以这里:
cb.setMethod(ClassA.methodA(n));
ClassA.methodA(n)
是一种方法调用,您无法将其分配给代理。
基本上,您无法在此阶段传递参数。您必须在调用委托时传递参数。 e.g。
del.Invoke(5);
但是你说你想总是写del.Invoke()
,没有参数。那么,你不应该使用Action<int>
,你应该使用Action
,它不接受任何参数。
class Program
{
public static void Main()
{
int n = 2;
ClassB cb = new ClassB();
cb.setMethod(() => ClassA.methodA(n));
}
}
public class ClassA
{
public static void methodA(int a)
{
//code
}
}
public class ClassB
{
Delegate del;
public void setMethod(Action action)
{
del = new Delegate(action);
}
public void ButtonClick()
{
del.Invoke();
}
}
public delegate void Delegate();
答案 1 :(得分:0)
cb.setMethod(new Action(ClassA.methodA));
答案 2 :(得分:0)
目前尚不清楚是否要在调用站点捕获整数(例如,作为闭包),或者是否要将参数明确传递给委托。
以下是前一种情况,其中捕获了值:
public static void Main()
{
var n = 2;
var cb = new ClassB();
cb.setMethod(() => ClassA.methodA(n));
}
委托因此不知道捕获的变量,只是定义为:
public delegate void Delegate();
但是如果你打算在调用时传递int,那么int的值需要在ButtonClick
中传递:
public static void Main()
{
var cb = new ClassB();
cb.setMethod(ClassA.methodA);
}
public class ClassB
{
Delegate del;
public void setMethod(Action<int> action)
{
del = new Delegate(action);
}
public void ButtonClick()
{
var n = 2;
del.Invoke(n);
}
}
public delegate void Delegate(int n);
编辑 - 重新认为有更好的方式
没有明确要求委托的真正理由。 Action
和Func
(以及Action<int>
,具体取决于上述内容)are already delegates。作为改进,您应该在调用之前检查操作是否已分配。 null条件运算符将简化为_action?.Invoke()
。但是你可以更进一步,并通过在构造函数中要求它来防止动作被取消分配:
public class ClassB
{
// Can be readonly if it is assigned only ever once, in the ctor.
private readonly Action _action;
public ClassB(Action action)
{
Contract.Assert(action != null);
_action = action;
}
public void ButtonClick()
{
_action(); // i.e. no need for Invoke or null check.
}
}