- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我有一个接受dynamic
参数的方法,还有一个不同参数的[CallerMemberName]
。只要动态对象也在参数中,就不会填充 [CallerMemberName]
参数。
这是 CallerMemberName
中的错误还是 C# 本身的错误?看下面的测试
static void Main(string[] args)
{
new CMNTest().BaseMethod();
}
public void BaseMethod()
{
NormalMethod();
dynamic myDyn = new Object();
DynamicArgumentMethod(myDyn);
ObjectArgumentMethod(new object());
ObjectArgumentMethod((object)myDyn);
}
public void NormalMethod([CallerMemberName]string methodName = null)
{
Console.WriteLine(methodName);
}
public void DynamicArgumentMethod(dynamic dynObject, [CallerMemberName]string methodName = null)
{
Console.WriteLine(methodName);
}
public void ObjectArgumentMethod(object otherArg, [CallerMemberName]string methodName = null)
{
Console.WriteLine(methodName);
}
输出:
BaseMethod
<null>
BaseMethod
BaseMethod
在 Visual Studio 和 LinqPad 中测试,结果相同。有办法解决这个问题吗?我需要对对象执行动态
操作,因此无法转换为对象
。
最佳答案
Is this a bug in the CallerMemberName or in C# itself?
没有;存在错误的假设就是错误。
C# CallerMemberName not working with dynamic in args?
没错。这是设计使然。这不是错误。
How does CallerMemberName work?
CallerMemberName 使用与可选参数相同的机制工作;如果您不了解这些机制,那么第一步就是了解它们。请参阅我关于该主题的文章:
http://ericlippert.com/tag/optional-arguments/
在继续之前阅读这些内容。
.....
好的,既然您已经了解可选参数是常量,由编译器在调用点插入,那么现在应该更容易理解调用者如何属性工作。它们是可选参数,替换为调用站点位置的“常量”。
现在想想“动态”是如何工作的。 “动态”意味着“在编译时放弃分析并在运行时重新启动编译器;确定编译器会做什么如果它在编译时知道运行时类型,并像编译器一样生成新代码会产生”。 编译器如何知道将当前位置作为常量保存到调用站点中?它需要这样做的事实是通过编译时重载解析发现的,您刚刚关闭了它.
在运行时运行的编译器没有关于源代码中原始调用位置的信息;该信息不会持久保存到调用站点中,因为原始编译时编译器没有理由相信它需要这样做。
顺便说一句,这与扩展方法无法动态分派(dispatch)的原因相同:调用站点有效负载不包括调用时“在范围内”的所有静态类。
不幸的是,这只是您为全动态调度付出的代价之一。
关于C# CallerMemberName 不能在 args 中使用动态?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24939677/
我正在使用 C#(.NET 4.5、VS 2013)生成一个序列化程序,我正在使用一个属性来控制序列化元数据,例如用于存储成员以供读取和写入的名称。因为我不想每次都写出成员名称作为属性的参数,所以我尝
我有以下日志方法(用于单元测试项目): public static void WriteLogFile(T obj, [System.Runtime.CompilerServices.
我有一个面向 Windows Phone 7.1+ 和 Windows 应用商店应用程序(适用于 WinRT)的可移植库,它使用 .net 4.5 框架。 我想在其中使用新的 [CallerMembe
现在(C# 4.0),我们的日志记录方法看起来像 public void Log(string methodName, string messageFormat, params object[] me
我正在浏览大约 700K 行代码。大量的接口(interface)实现和DI使用。我试图找出从哪里调用特定方法,因此我尝试使用 [CallerMemberName]。 我在谷歌等上看到的所有例子都是这
使用CallerMemberName/CallerFilePathAttribute/CallerLineNumber属性如何影响应用程序的性能?这是在应用程序中编译的东西,还是相关反射的东西,还是其
我有一个接受dynamic 参数的方法,还有一个不同参数的[CallerMemberName]。只要动态对象也在参数中,就不会填充 [CallerMemberName] 参数。 这是 CallerMe
有没有办法在调用方方法中获取变量/参数的原始名称?在某种程度上,它就像 [CallerMemberName]属性,但对于变量/参数。 更新 2018.02: 这个问题与这些问题类似:1 , 2和 3
我正在尝试在我的新 WPF 4.5 CompositeWPF (Prism) 项目中实现日志记录功能。这需要我在我的代码中实现 ILoggerFacade。该接口(interface)只实现了1个方法
新的 C# 5.0 版本引入了一些东西来摆脱 INotifyPropertyChanged 实现中的“魔法字符串”,例如: OnPropertyChanged("CustomerName"); 现在可
我刚刚安装了 Visual Studio 2012,因此我可以利用更好的方法通过 Silverlight 实现 MVVM。 我想做的第一件事是开始使用 [CallerMemberName] 属性,这样
有什么区别以及对代码的影响? 关于性能和限制,什么更适合? 新属性: - [调用文件路径属性] - [CallerMemberName] - [来电号码] 现在它们在 .NET 4 中也可用(它很容易
有好文章推荐different ways for implementing INotifyPropertyChanged . 考虑以下基本实现: class BasicClass : INotifyP
我正在尝试实现与提升属性一起使用的 CallerMemberName。我试图在 vb 中执行此操作,但在 system.runtime.compilerservices 中找不到此接口(interfa
我在类的 INotifyPropertyChanged 实现中使用了 CallerMemberName 属性,如 MSDN 中所述如下: public event PropertyChange
快速背景:尝试创建一个方法,该方法将根据调用它的方法返回预定义的字符串。 (有点掩饰但足够接近)。 我打算使用 [ CallerMemberName ] 属性,但我的问题是: => 我是否需要将 Me
如何CallerMemberName实现了吗? 我明白它的作用 - 它允许我们在代码中保留魔法字符串 - 但它应该用于 nameof 吗?什么更高效? 有什么区别/CallerMemberName 究
我正在尝试通过 BCL 可移植包在 .NET 4.0 中使用 CallerMemberName 属性。它总是返回一个空字符串而不是成员名称。我做错了什么? public partial class F
因此,.NET 4.5 引入了 CallerMemberNameAttribute,对于任何使用 WPF 并实现 INotifyPropertyChanged 的人来说,这似乎是天赐之物 - 我的问题
我是一名优秀的程序员,十分优秀!