Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 为什么我不能将Debug.Assert()与接受动态并返回bool的方法一起使用?_C#_.net_Dynamic_Conditional Attribute - Fatal编程技术网

C# 为什么我不能将Debug.Assert()与接受动态并返回bool的方法一起使用?

C# 为什么我不能将Debug.Assert()与接受动态并返回bool的方法一起使用?,c#,.net,dynamic,conditional-attribute,C#,.net,Dynamic,Conditional Attribute,这是我的密码: class Program { static void Main(string[] args) { dynamic param = null; System.Diagnostics.Debug.Assert(whatever(param)); } static bool whatever(object param) { return true; } } 当我运行它时,我会收到带有以

这是我的密码:

class Program
{
    static void Main(string[] args)
    {
        dynamic param = null;
        System.Diagnostics.Debug.Assert(whatever(param));
    }

    static bool whatever(object param)
    {
        return true;
    }
}
当我运行它时,我会收到带有以下消息的
RuntimeBinderException

无法动态调用方法“Assert”,因为它具有条件属性

是的,
Assert()
上有
ConditionalAttribute
。然而,不管该方法接受什么,只有一个
whater()
方法返回
bool


运行时到底抱怨什么?为什么它不能使用
bool
并将其传递到
Assert()

Main
中的实际调用被转换为
CallSite
,因为您使用
动态参数调用调用。
CallSite
完成了在运行时调用此方法所需的所有准备工作。但是,问题是,
Assert
有一个
Conditional
属性,这意味着它需要在编译时将信息传递给编译器预处理器

这:

可以将条件属性放置在方法(和中的属性)上 whidbey)指示编译器有条件地删除对 未定义符号时的函数。这仅对调试有用 功能,比如Debug.Assert,它在 它

条件接受字符串参数如果该字符串被定义为 由编译器的预处理器确定),然后编译器发出 方法调用。如果没有定义符号,C#仍然编译 方法,但不编译调用。

后来,为了加强我们的观点:

条件属性完全由编译器处理,无需 运行时的任何合作。该方法仍处于正常JIT状态, 但是如果符号不存在,编译器就不会发出调用 定义

现在,我们有了冲突。我们不能在运行时将参数传递给编译器预处理器(告诉它是否定义了“DEBUG”),只能在编译时传递,但该方法只能在运行时调用,因为我们将在运行时推断
动态
值的类型

这就是为什么绑定器在运行时大喊这个方法实际上不能被调用,因为这会破坏
条件属性

奖金: 这就是所谓的:

private static void Main(string[] args)
{
    object param = null;
    if (Program.<Main>o__SiteContainer0.<>p__Site1 == null)
    {
        Program.<Main>o__SiteContainer0.<>p__Site1 = CallSite<Action<CallSite, Type, object>>.Create(Binder.InvokeMember(CSharpBinderFlags.ResultDiscarded, "Assert", null, typeof(Program), new CSharpArgumentInfo[]
        {
            CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.UseCompileTimeType | CSharpArgumentInfoFlags.IsStaticType, null),
            CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null)
        }));
    }
    Action<CallSite, Type, object> arg_CB_0 = Program.<Main>o__SiteContainer0.<>p__Site1.Target;
    CallSite arg_CB_1 = Program.<Main>o__SiteContainer0.<>p__Site1;
    Type arg_CB_2 = typeof(Debug);
    if (Program.<Main>o__SiteContainer0.<>p__Site2 == null)
    {
        Program.<Main>o__SiteContainer0.<>p__Site2 = CallSite<Func<CallSite, Type, object, object>>.Create(Binder.InvokeMember(CSharpBinderFlags.None, "whatever", null, typeof(Program), new CSharpArgumentInfo[]
        {
            CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.UseCompileTimeType | CSharpArgumentInfoFlags.IsStaticType, null),
            CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null)
        }));
    }
    arg_CB_0(arg_CB_1, arg_CB_2, Program.<Main>o__SiteContainer0.<>p__Site2.Target(Program.<Main>o__SiteContainer0.<>p__Site2, typeof(Program), param));
private static void Main(字符串[]args)
{
对象参数=null;
if(Program.o_uuuSiteContainer0.p_uuuSite1==null)
{
Program.o__SiteContainer0.p__Site1=CallSite.Create(Binder.InvokeMember(CSharpBinderFlags.resultDiscarted,“Assert”,null,typeof(Program),new csharpbargumentinfo[]
{
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.UseComileTimeType | CSharpArgumentInfoFlags.IsStaticType,null),
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None,null)
}));
}
Action arg_CB_0=Program.o_uusiteecontainer0.p_usite1.Target;
CallSite arg_CB_1=Program.o_site容器0.p_Site1;
类型arg_CB_2=类型(调试);
if(Program.o_uuuSiteContainer0.p_uuuSite2==null)
{
Program.o__SiteContainer0.p__Site2=CallSite.Create(Binder.InvokeMember(CSharpBinderFlags.None,“whatever”,null,typeof(Program),new CSharpArgumentInfo[]
{
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.UseComileTimeType | CSharpArgumentInfoFlags.IsStaticType,null),
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None,null)
}));
}
arg_CB_0(arg_CB_1,arg_CB_2,Program.o_SiteContainer0.p_Site2.Target(Program.o_SiteContainer0.p_Site2,typeof(Program),param));

试试
Assert((bool)whatever(param))
@lucastrezesniewski:这比更明显的
Assert(whatever((object)param))更有趣。
(也有效)。毫无疑问,语言规范将在某个地方解释为什么对
whatever
的调用是动态绑定的,即使没有其他方法可以调用。@Sriram Sakthivel:我看不出这个问题与那个问题是如何重复的。链接的问题不是重复的。尽管它提供了大致相同的解决方法d、 它没有回答为什么。@sharptooth我看不出这个问题怎么不是?你没有传递bool。它被键入为
dynamic
,这正是编译器所抱怨的。即使返回bool,动态表达式的结果总是动态的。你需要在那里进行强制转换。你是如何获得这段代码的?@sharptooth Via