很多时候,我们需要在运行过程中记录一些调测的日志信息,如下所示:

public void DoProcessing()
{
TraceMessage("DoProcessing()被XXX调用");//这里需要知道当前谁调用了DoProcessing(),由于我们并不知道是谁调用了DoProcessing(),所以字符串中的XXX不得而知,无法将完整的日志信息用TraceMessage方法记入日志
}

上面TraceMessage("DoProcessing()被XXX调用")中的XXX我们获取不到,导致日志记录不完全。 此外为了调测方便,除了事件信息外,我们往往还需要知道发生该事件的代码位置以及调用栈信息。在C++中,我们可以通过定义一个宏,然后在宏中通过__FILE__和__LINE__来获取当前代码的位置,但C#并不支持宏,往往只能通过StackTrace来实现这一功能,但StackTrace却又不是很靠谱,常常获取不了我们所要的结果。

针对这个问题,在.Net 4.5(.NET Core中也可使用)中引入了三个Attribute:CallerMemberName、CallerFilePath和CallerLineNumber。在编译器的配合下,分别可以获取到调用函数(准确讲应该是成员)名称,调用文件及调用行号。上面的TraceMessage函数可以实现如下:

class Program
{
public static void TraceMessage(string message,
[CallerMemberName] string memberName = null,
[CallerFilePath] string sourceFilePath = null,
[CallerLineNumber] int sourceLineNumber = default(int))
{
Debug.WriteLine("message: " + message);
Debug.WriteLine("member name: " + memberName);
Debug.WriteLine("source file path: " + sourceFilePath);
Debug.WriteLine("source line number: " + sourceLineNumber);
}
static void Main(string[] args)
{
TraceMessage("Hello world");
}
}

在VisualStudio的输出窗口中输出结果如下:

message: Hello world
member name: Main
source file path: C:\Users\Scott\source\repos\ConsoleApp1\ConsoleApp1\Program.cs
source line number: 21

另外,在构造函数,析构函数、属性等特殊的地方调用CallerMemberName属性所标记的函数时,获取的值有所不同,其取值如下表所示:

调用的地方

CallerMemberName获取的结果

方法、属性或事件

方法,属性或事件的名称

构造函数

字符串 ".ctor"

静态构造函数

字符串 ".cctor"

析构函数

该字符串 "Finalize"

用户定义的运算符或转换

生成的名称成员,例如, "op_Addition"。

特性构造函数

特性所应用的成员的名称

例如,对于在属性中调用CallerMemberName所标记的函数即可获取属性名称,通过这种方式可以简化 INotifyPropertyChanged 接口的实现。关于调用方信息更详细的资料,请参看MSDN:http://msdn.microsoft.com/zh-cn/library/hh534540.aspx

原文链接

C# 5.0中使用CallerMemberName、CallerFilePath和CallerLineNumber获取代码的调用方信息(转载)的更多相关文章

  1. C#5.0新增功能02 调用方信息

    连载目录    [已更新最新开发文章,点击查看详细] 通过使用调用方信息特性,可获取有关方法的调用方的信息. 可以获取源代码的文件路径.源代码中的行号和调用方的成员名称. 此信息有助于跟踪.调试和创建 ...

  2. VC6.0 中 添加/取消 块注释的Macro代码

    SAMPLE.DSM是微软提供的样例,使用的是vb语言.其中的 CommentOut 函数,是支持块注释的,可是这种/**/的注释方式,有时候用起来不是很方便,因为两个/会因为一个/而终止.对于大块代 ...

  3. asp.Net2.0中TextBox设置只读后后台获取不到值的解决方法

    http://www.cnblogs.com/yxyht/archive/2013/03/02/2939883.html   ASP.NET中TextBox控件设置ReadOnly="tru ...

  4. TC9.0新增实用接口,用AutoHotkey获取当前选中文件等信息

    TC9.0的history.txt里有几行更新说明(见文章末尾),可以用SendMessage命令获取信息, 消息号是WM_USER+50(即1074),wParam则是更新说明里的内容, 下面是我简 ...

  5. C# 5.0中新增特性

    C# 5.0随着VisualStudio 2012一起正式发布了,让我们来看看C#5.0中增加了哪些功能. 1. 异步编程 在.Net 4.5中,通过async和await两个关键字,引入了一种新的基 ...

  6. ASP.NET Core 1.0 中的依赖项管理

    var appInsights=window.appInsights||function(config){ function r(config){t[config]=function(){var i= ...

  7. .NET 中获取调用方法名

    在写记录日志功能时,需要记录日志调用方所在的模块名.命名空间名.类名以及方法名,想到使用的是反射(涉及到反射请注意性能),但具体是哪一块儿还不了解,于是搜索,整理如下: 需要添加相应的命名空间: us ...

  8. C# 特性学习之一、CallerMemberName、CallerFilePath和CallerLineNumber

    在开发中经常会写个公有静态类记录日志,如下: /// <summary> /// Writes the error. /// </summary> /// <param ...

  9. 在 .NET 4.0 中使用 .NET 4.5 中新增的特性(CallerMemberNameAttribute/CallerFilePathAttribute/CallerLineNumberAttribute)

    介绍 标题中所说的三个特性 CallerMemberNameAttribute / CallerFilePathAttribute / CallerLineNumberAttribute 我们统称为调 ...

随机推荐

  1. UNION ALL 视图 'ImprotHIS2012.dbo.ImportHISData' 不可更新,因为没有找到分区依据列。 Severity 16 State 12

    -- 3 更正措施,使约束check一次 Alter Table ImprotHIS_Bak_2011.dbo.ImportHISData with check Check Constraint al ...

  2. 远程连接Redis服务器

    建立了一个redis服务器,那么其他主机应该怎么连接上呢? /** * * 修改redis.conf配置文件 * */ // 1. 注释掉bind绑定配置 // 2. 搜索并修改为 protected ...

  3. Python入门-初始面向对象

    之前我们代码基本上都是面向过程的,今天我们就来初始一下python中一个重要的内容:面向对象 一.面向对象和面向过程(重点理解) 1.面向过程: 一切以事物的流程为核心. 核心是"过程&qu ...

  4. 点击空白处--某个div 消失

    背景:1.需要在 easyui grid 的编辑框 获取焦点的时候,在正下方展示费用类型的网格 2.在点击费用类型网格以外的地方,该网格消失 思路: 一.用easyui 的panel 作为费用类型网格 ...

  5. File中mkdir()和mkdirs()的区别

    mkdir() 创建此抽象路径名指定的目录.只能在已经存在的目录中创建文件夹 如: File folder = new File("d:\\test1\\test2"); fold ...

  6. Office - InfoPath

    1. 移除隐藏空间后剩余的空白: http://social.technet.microsoft.com/Forums/sharepoint/zh-TW/3dea3014-f808-428b-b283 ...

  7. Android 文件的可读可写

    文件流形式的保存,获取: 设立文件的私有,可读,可写,公开: 效果图: /data/data中文件夹: 新建一个项目测试文件: 得到data/data,查看文件的特性:

  8. JavaScript中sort()方法

    sort()方法主要是用于对数组进行排序,默认情况下该方法是将数组元素转换成字符串,然后按照ASC码进行排序,这个大家都能理解,但如果数组元素是一个Object呢,转不了字符串,难道不能进行排序?答案 ...

  9. qt 样式表基本用法

    Qt样式表 QT样式表参考CSS层叠样式表设计,不同之处在于QT样式表应用于Widget世界. 可以使用QApplication::setStyleSheet()函数设置到整个应用程序上,也可以使用Q ...

  10. matlab练习程序(三角形外接圆)

    三角形两边的垂直平分线就能确定外接圆. 结果如下: matlab代码如下: clear all;close all;clc; p=rand(,); %(x,y) cen1=(p(,:)+p(,:))/ ...