0. 目录

C#6 新增特性目录

1. 老版本的代码

 internal class Person
{
public string Name { get; set; }
public int Age { get; set; } public override string ToString()
{
return string.Format("[name={0},age={1}]", Name, Age);
}
}

通常我们在格式化字符串的时候会使用string的静态方法Format来进行字符串拼接,然后使用{0}...{n}来充当占位符。如果{n}过大,代码的可读性就会急剧下降,C#6引入一个新语法来简化这种书写方式。

2. $"{xxx:}"

我们之间来看新语法:

 internal class Person
{
public string Name { get; set; }
public int Age { get; set; } public override string ToString()
{
return $"[name={Name},age={Age}]";
}
}

新语法采用 $  开头,然后把之前的{n}换成了有意义的表达式,直观且简洁,且在VS2015中会有智能提示。好了,基本用法就是这样,按老习惯,对比下IL代码吧。

老版本的IL:

 .method public hidebysig virtual instance string
ToString() cil managed
{
// Code size 33 (0x21)
.maxstack
.locals init ([] string V_0)
IL_0000: nop
IL_0001: ldstr "[name={0},age={1}]"
IL_0006: ldarg.
IL_0007: call instance string csharp6.Person::get_Name()
IL_000c: ldarg.
IL_000d: call instance int32 csharp6.Person::get_Age()
IL_0012: box [mscorlib]System.Int32
IL_0017: call string [mscorlib]System.String::Format(string,
object,
object)
IL_001c: stloc.
IL_001d: br.s IL_001f
IL_001f: ldloc.
IL_0020: ret
} // end of method Person::ToString

新语法的IL:

 .method public hidebysig virtual instance string
ToString() cil managed
{
// Code size 33 (0x21)
.maxstack
.locals init ([] string V_0)
IL_0000: nop
IL_0001: ldstr "[name={0},age={1}]"
IL_0006: ldarg.
IL_0007: call instance string csharp6.Person::get_Name()
IL_000c: ldarg.
IL_000d: call instance int32 csharp6.Person::get_Age()
IL_0012: box [mscorlib]System.Int32
IL_0017: call string [mscorlib]System.String::Format(string,
object,
object)
IL_001c: stloc.
IL_001d: br.s IL_001f
IL_001f: ldloc.
IL_0020: ret
} // end of method Person::ToString

第一眼看到新版本的IL代码,我还以为我没有重新编译我的代码。C#编译器帮我们转成了老版本的写法而已,一模一样的。。。so,这又是一个语法层面的优化。

3. Example

 //支持方法调用
string s1 = $"{person.GetHashCode()}";
//支持表达式
string s2 = $"person.{nameof(person.Name)} is {person?.Name}";
//支持格式化输出
DateTime now = DateTime.Now;
string s3 = $"DateTime.Now={now:yyyy-MM-dd HH:mm:ss}";
//组合表达式和格式化输出
string s4 = $"{person.Name,2} is {person.Age:D2} year{(person.Age == 1 ? "" : "s")} old.";
//支持的隐式类型转换
IFormattable s5 = $"Hello, {person.Name}";
FormattableString s6 = $"Hello, {person.Name}"

新语法支持表达式求值,支持:格式化操作,还支持到IFormattable的隐式转换,编译结果是利用 System.Runtime.CompilerServices.FormattableStringFactory.Create 这个静态方法构造一个 FormattableString 实现的。IL如下:

 IL_0095:  stloc.s s4
IL_0097: ldstr "Hello, {0}"
IL_009c: ldc.i4.1
IL_009d: newarr[mscorlib] System.Object
IL_00a2: dup
IL_00a3: ldc.i4.0
IL_00a4: ldloc.0
IL_00a5: callvirt instance string csharp6.Person::get_Name()
IL_00aa: stelem.ref
IL_00ab: call class [mscorlib]System.FormattableString[mscorlib] System.Runtime.CompilerServices.FormattableStringFactory::Create(string,object[])
IL_00b0: stloc.s s5
IL_00b2: ldstr "Hello, {0}"
IL_00b7: ldc.i4.1
IL_00b8: newarr[mscorlib] System.Object
IL_00bd: dup
IL_00be: ldc.i4.0
IL_00bf: ldloc.0
IL_00c0: callvirt instance string csharp6.Person::get_Name()
IL_00c5: stelem.ref
IL_00c6: call class [mscorlib]System.FormattableString[mscorlib] System.Runtime.CompilerServices.FormattableStringFactory::Create(string,object[])

4. 参考

Interpolated Strings

[C#6] 4-string 插值的更多相关文章

  1. C#6新特性,让你的代码更干净

    前言 前几天看一个朋友的博客时,看他用到了C#6的特性,而6出来这么长时间还没有正儿八经看过它,今儿专门看了下新特性,说白了也不过是语法糖而已.但是用起来确实能让你的代码更加干净些.Let's try ...

  2. [C#6] 0-概览

    1. C#6 新特性图谱 C#6的新特性主要由编译器(“Roslyn”)带来,并不依赖CLR和.NET Framework的升级,我们可以认为这个版本的新语言特性的主要目的为了简化代码书写方式,让我们 ...

  3. JVM 平台上的各种语言的开发指南

    JVM 平台上的各种语言的开发指南 为什么我们需要如此多的JVM语言? 在2013年你可以有50中JVM语言的选择来用于你的下一个项目.尽管你可以说出一大打的名字,你会准备为你的下一个项目选择一种新的 ...

  4. Groovy中String转换Gstring用于动态插值

    知识点是Groovy中的模板引擎 GStringTemplateEngine 第一个例子: def binding = [ firstname : "Grace", lastnam ...

  5. 窥探Swift之字符串(String)

    之前总结过Objective-C中的字符串<Objective-C精选字符串处理方法>,学习一门新语言怎么能少的了字符串呢.Swift中的String和Objective-C语言中NSSt ...

  6. 用JAVA实现插值查询的方法(算近似值,区间求法)

    插值查询:如果有这样一张表,有一列叫水位,有一列叫库容,比如下面的图. 我现在想做这么一件事情:对于这个测站而言,当我输入某一个水位或者库容的时候,想要查询到对应的水位或者库容呢? 而这个值不一定是存 ...

  7. 关于IDW空间插值

    空间插值一般都会用到IInterPolationOP接口等 首先是通过图层的名称获取图层的方法: private ILayer GetLayerByName(string name)        { ...

  8. 你需要知道的Sass插值

    你也许会不时地写写 Sass 玩玩,你也会很享受它带给你各种便利.但还有一件事,你并不一定完全了解:插值 (interpolation) - 将一个占位符,替换成一个值.好了,你们都很幸运,因为今天我 ...

  9. iOS -Swift 3.0 -String(字符串常规用法)

    // // ViewController.swift // Swift-String // // Created by luorende on 16/9/10. // Copyright © 2016 ...

  10. iOS - Swift String 字符串

    前言 public struct String public class NSString : NSObject, NSCopying, NSMutableCopying, NSSecureCodin ...

随机推荐

  1. 排名前 8 的 PHP 调试工具

    Web 开发并不是一项轻松的任务,有超级多服务端脚本语言提供给开发者,但是当前 PHP 因为具有额外的一些强大的功能而越来越流行.PHP 是最强大的服务端脚本语言之一,同时也是 web 开发者和设计者 ...

  2. Git代码管理工具

    Git代码管理工具 Git 是分布式的源代码管理工具,这点区别于svn -让源代码可以被追溯,主要是记录了每次的更新了什么,如果新版本不想用,那么则可以退回之前的版本 -Git 是Linux之父当年为 ...

  3. 前端项目构建之yeoman

    各位好啊,我又和大家见面了,也许你已经不记得大明湖畔的容嬷嬷,但是只要记得博客园中的我就好,希望我的博客能像一股清风,为你驱散炎热的酷暑,好了,废话不多说,开始上干货,我今天带给大家的是前端工程化开发 ...

  4. struts2学习笔记--使用Validator校验数据

    我们在进行一些操作是需要对用户的输入数据进行验证,比如网站的注册,需要对各个数据项进行数据校验,Struts2提供了一些默认的校验器,比如数字的检测,邮箱的检测,字符串长度的检测等等. 常用的Vali ...

  5. JQuery中使用Ajax实现诸如登录名检测等异步请求Demo

    上一篇博客介绍了注册登录时一次性图形验证码的工具类的编写,这篇随笔同样是我在写用jquery中ajax实现登录信息检测的异步请求功能的笔记,在各个网站进行信息用户注册时,需要在不刷新页面的情况下对注册 ...

  6. 移动端用js与jquery实时监听输入框值的改动

    背景: 在一次移动端H5开发中,需要监听输入框值的实时变动. onchange事件肯定抛弃,因为只能失去焦点才触发. 而keyPress在Android可以触发,iOS不可以. 又不想用Android ...

  7. 利用Angularjs测试引擎Karma进行自动化单元测试

    Karma是Google用于angularjs框架单元测试的js引擎(javascript test runner ), angular1 和angular2项目源码的单元测试都是基于karma和ja ...

  8. jQuery效率提升建议

    jQuery简洁通用的方法集把编码者从繁重的工作中解脱出来,也拉低了进入javascript的门槛,初学者对浏览器兼容性一无所知的情况下,几行代码就可以写出超炫的特效.网上有一篇文章转载比较泛滥,已经 ...

  9. 让 select 的 option 标签支持事件监听(如复制操作)

    这标题,让option支持事件监听,应该不难的呀,有什么好讲的? 其实还是有的,默认在浏览器代码是无法直接对option标签进行操作的,不仅包括JS事件监听,还是CSS样式设置 查了一些资料,姑且认为 ...

  10. clr enabled Server Configuration Option

    在SQL Server中启用CLR,可以执行下面SQL语句: EXEC sp_configure 'clr enabled'; '; RECONFIGURE; Source Code