Caller Information

  CallerInformation是一个简单的新特性,包括三个新引入的Attribute,使用它们可以用来获取方法调用者的信息,

  这三个Attribute在System.Runtime.CompilerServices命名空间下,分别叫做CallerMemberNameAttribute,CallerFilePathAttribute和CallerLineNumberAttribute。

CallerMemberNameAttribute:用来获取方法调用者的名称
CallerFilePathAttribute:用来获取方法调用者的源代码文件路径
CallerLineNumberAttribute:用来获取方法调用者所在的行号

  简单看一个小例子:

using System;
using System.Runtime.CompilerServices; class Program
{
static void Main(string[] args)
{
DoProcessing();
Console.ReadKey();
} static void DoProcessing()
{
TraceMessage("Something happened.");
} static void TraceMessage(string message,
[CallerMemberName] string memberName = "",
[CallerFilePath] string sourceFilePath = "",
[CallerLineNumber] int sourceLineNumber = 0)
{
Console.WriteLine("message: " + message);
Console.WriteLine("member name: " + memberName);
Console.WriteLine("source file path: " + sourceFilePath);
Console.WriteLine("source line number: " + sourceLineNumber);
}
}

不用多说了,结果很清楚。

  不过需要注意,Caller Info的这些Attribute只能用在optional parameter上,也就是说要指定默认值的。
  此外对于CallerMemberNameAttribute需要多说一点,使用这个Attribute可以避免在程序中硬编码调用方的函数名,至于这个属性返回的名字一般是这样的:

调用方法的类型 获取的结果
方法,属性,事件 方法,属性或事件的名字
构造函数 字符串".ctor"
静态构造函数 字符串".cctor"
Finalize函数 字符串"Finalize"
用户自定义的操作 编译产生的名字,比如"op_Addition"
Attribute构造函数 应用此Attribute的成员函数名字。如果不是应用于成员的Attribute,比如说是应用于类型的Attribute,则使用其设置的默认值

  这个特性在WPF的MVVM模式中很有用。在WPF的MVVM设计模式中的viewmodel里,我们是用INotifyPropertyChanged接口去通知在viewmodel里的改变。具体实现中很多的Binding是通过字符串来标识的,当修改一个Property的名字的时候,有时候很可能会忘记更新通知中的字符串名字,使用这个新的CallerMemberNameAttribute就能避免这个问题。
  例如以前通常的一种实现是这样的:

public class EmployeeVM:INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged; public void OnPropertyChanged(string propertyName)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
} private string _name; public string Name
{
get { return _name; }
set
{
_name = value;
OnPropertyChanged("Name");
}
}
}

这种实现中Property的名字"Name"是以字符串的形式来约定的,一旦这个Property被Rename后忘记改了此处,就会带来bug。使用新的Attribute以后就可以这么写了:

public class EmployeeVM:INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged; public void OnPropertyChanged([CallerMemberName] string propertyName=null)
{
if (PropertyChanged != null)
{
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
} private string _name; public string Name
{
get { return _name; }
set
{
_name = value;
OnPropertyChanged();
}
}
}

这么一来就不用硬编码了,简单。

C#的变迁史 - C# 5.0 之调用信息增强篇的更多相关文章

  1. C#的变迁史 - C# 4.0 之线程安全集合篇

    作为多线程和并行计算不得不考虑的问题就是临界资源的访问问题,解决临界资源的访问通常是加锁或者是使用信号量,这个大家应该很熟悉了. 而集合作为一种重要的临界资源,通用性更广,为了让大家更安全的使用它们, ...

  2. C#的变迁史 - C# 5.0 之并行编程总结篇

    C# 5.0 搭载于.NET 4.5和VS2012之上. 同步操作既简单又方便,我们平时都用它.但是对于某些情况,使用同步代码会严重影响程序的可响应性,通常来说就是影响程序性能.这些情况下,我们通常是 ...

  3. C#的变迁史 - C# 4.0 之并行处理篇

    前面看完了Task对象,这里再看一下另一个息息相关的对象Parallel. Parallel对象 Parallel对象封装了能够利用多核并行执行的多线程操作,其内部使用Task来分装多线程的任务并试图 ...

  4. C#的变迁史 - C# 4.0篇

    C# 4.0 (.NET 4.0, VS2010) 第四代C#借鉴了动态语言的特性,搞出了动态语言运行时,真的是全面向“高大上”靠齐啊. 1. DLR动态语言运行时 C#作为静态语言,它需要编译以后运 ...

  5. C#的变迁史 - C# 4.0 之多线程篇

    在.NET 4.0中,并行计算与多线程得到了一定程度的加强,这主要体现在并行对象Parallel,多线程Task,与PLinq.这里对这些相关的特性一起总结一下. 使用Thread方式的线程无疑是比较 ...

  6. C#的变迁史 - C# 3.0篇

    C# 3.0 (.NET 3.5, VS2008) 第三代C#在语法元素基本完备的基础上提供了全新的开发工具和集合数据查询方式,极大的方便了开发. 1. WPF,WCF,WF 这3个工程类型奠定了新一 ...

  7. C#的变迁史 - C# 2.0篇

    在此重申一下,本文仅代表个人观点,如有不妥之处,还请自己辨别. 第一代的值类型装箱与拆箱的效率极其低下,特别是在集合中的表现,所以第二代C#重点解决了装箱的问题,加入了泛型.1. 泛型 - 珍惜生命, ...

  8. C#的变迁史 - C# 5.0 之其他增强篇

    1. 内置zip压缩与解压 Zip是最为常用的文件压缩格式之一,也被几乎所有操作系统支持.在之前,使用程序去进行zip压缩和解压要靠第三方组件去支持,这一点在.NET4.5中已有所改观,Zip压缩和解 ...

  9. C#的变迁史 - C# 1.0篇

    C#与.NET平台诞生已有10数年了,在每次重大的版本升级中,微软都为这门年轻的语言添加了许多实用的特性,下面我们就来看看每个版本都有些什么.老实说,分清这些并没什么太大的实际意义,但是很多老资格的. ...

随机推荐

  1. ThreadStatic应用(Identity补完)

    关于Identity Identity自增序列/唯一断标识 起初做这个东西,是在一个内部组件中,用于在高并发的环境下得到一个较短的“相对”不重复标识字符串;(这里说的相对是指一定的数量下不重复) 灵感 ...

  2. MVVM架构~Knockoutjs系列之text,value,attr,visible,with的数据绑定

    返回目录 Knockoutjs是微软mvc4里一个新东西,用这在MVC环境里实现MVVM,小微这次没有大张旗鼓,而是愉愉的为我们开发者嵌入了一个实现MVVM的插件,这下面的几篇文章中,我和大家将一起去 ...

  3. ToString()的各种用法(大全)

    常用例子: string str = ""; str = .ToString("N"); //生成 12,3456.00 str = .ToString(&qu ...

  4. Linq 查询结果 可能遵循 2 º,2¹,2 ²,......增长计算

    static void Main(string[] args) { , , , , , , , , }; var obj = from item in array orderby item ascen ...

  5. CSS中的::after ::before

    利用::after和before来清除浮动 <!DOCTYPE html> <html lang="en"> <head> <meta c ...

  6. switch判断注意点

    if判断,如果判断的两个值类型不同,会继续隐性转换,==,当然如果使用===就不会. 1 if(2=="2"){ 2 console.log("true"); ...

  7. uva 10801 - Lift Hopping(最短路Dijkstra)

    /* 题目大意: 就是一幢大厦中有0-99的楼层, 然后有1-5个电梯!每个电梯有一定的上升或下降速度和楼层的停止的位置! 问从第0层楼到第k层最少经过多长时间到达! 思路:明显的Dijkstra , ...

  8. python类定义与c#的一些区别

    c#中可以定义一个空类,但是python中定义空类需要加pass class EmptyClass(object): pass python的lei是多继承   python子类继承了基类,如果子类也 ...

  9. nodejs在Liunx上的部署生产方式-PM2

    先安装:npm install -g pm2 (注意:使用它要先安装它,用root账号和全局模式安装一下) 安装完成使用:pm2 -v 查看版本信息 安装成功之后,启动nodejs项目:pm2 sta ...

  10. .Net Request.Form含有危险字符的处理办法

    今天我们的网站遇到一个问题,下标就类似于化学分子式这样的是需要用"<sub></sub>"这个标签括起来的,当时没有转义,有部分标签就显示不出来了, 后来我 ...