[关闭]
@muyanfeixiang 2016-02-21T22:23:57.000000Z 字数 2241 阅读 1363

C# 7 新特性-1

C#


Tuples

What

Tuples是数据的临时分组。区别与struct和class,后两者需要预先定义。

Why

数据临时分组的最常用场景就是方法的返回值。目前有三种方式。

Out 参数

  1. public void GetLatLng(string address, out double lat, out double lng) { ... }
  2. double lat, lng;
  3. GetLatLng(myValues, out lat, out lng);
  4. Console.WriteLine($"Lat: {lat}, Long: {lng}");

这种方法的缺点就是不能对async方法使用,还必须提前声明变量,out参数声明时还不能使用var。

Tuple-type

  1. public Tuple<int, int> GetLatLng(string address) { ... }
  2. var latLng = GetLatLng("some address");
  3. Console.WriteLine($"Lat: {latLng.Item1}, Long: {latLng.Item2}");

这种方式没有Out参数的缺点,但是因为tuple的返回值是item1和item2之类的,含义不清晰。

class/struct

  1. struct LatLng{ public double Lat; public double Lng;}
  2. public LatLng GetLatLng(string address) { ... }
  3. var ll= GetLatLng("some address");
  4. Console.WriteLine($"Lat: {ll.Lat}, Long: {ll.Lng}");

这个缺点就是比较啰嗦和无意义的overhead(如果返回类型仅使用一次的话)

How

在c#7中有几种不同的方式可以满足这种场景。

Tuple return types

就是多返回值的情形,如下

  1. public (double lat, double lng) GetLatLng(string address) { ... }
  2. var ll = GetLatLng("some address");
  3. Console.WriteLine($"Lat: {ll.lat}, Long: {ll.lng}");

内联tuples

可以如下创建tuples

  1. var ll = new (double lat, double lng) { lat = 0, lng = 0 };

tuple解构

因为将数据捆绑作为概念不是那么重要,所以可能你不想通过捆绑获取数据,而是直接获取。所以你可以直接结构多返回值而不是通过捆绑的tuple(即返回的变量ll)。

  1. (var lat, var lng) = GetLatLng("some address");
  2. Console.WriteLine($"Lat: {lat}, Long: {lng}");

Record类型

是什么

Record类型是属性的简单打包,数据类型中只有属性。

为什么

class和struct仅仅包含属性的情况下,仍然需要一大对声明,相当繁琐。如下

  1. class MyPoint
  2. {
  3. int _x;
  4. int _y;
  5. int _z;
  6. MyPoint(int x, int y, int z){
  7. this._x = x;
  8. this._y = y;
  9. this._z = z;
  10. }
  11. public int X {get{ return this._x;}}
  12. public int Y {get{ return this._y;}}
  13. public int Z {get{ return this._z;}}
  14. }

How

有了Record类型,你可以一行实现。如下

  1. class Point(int X, int Y, int Z);

而且代码后面替你做了更多事情。
1.类会自动实现IEquatable,这样你可以基于他们的值来比较两个Record类型,而不是引用。
2.ToString方法会输出record中的值。

模式匹配

是什么

有了record类型,我们能使用内置的模式匹配。模式匹配意味着you can switch on the type of data you have to execute one or the other statement.

为什么

尽管模式匹配有点像if/else,但是还是有自身的优势的。
1.你可以对任何数据类型做模式匹配,即使自定义类型,而if/else需要基础类型来match
2.模式匹配可以从表达式中抽取值。(意思应该是可以根据表达式的类型来匹配)

How

模式匹配如下

  1. class Geometry();
  2. class Triangle(int Width, int Height, int Base) : Geometry;
  3. class Rectangle(int Width, int Height) : Geometry;
  4. class Square(int width) : Geometry;
  5. Geometry g = new Square(5);
  6. switch (g)
  7. {
  8. case Triangle(int Width, int Height, int Base):
  9. WriteLine($"{Width} {Height} {Base}");
  10. break;
  11. case Rectangle(int Width, int Height):
  12. WriteLine($"{Width} {Height}");
  13. break;
  14. case Square(int Width):
  15. WriteLine($"{Width}");
  16. break;
  17. default:
  18. WriteLine("<other>");
  19. break;
  20. }

如上可以看到如何对数据类型进行模式匹配,以及对其立即解构。

结论

如上仅仅是即将到了的c#新特性中的三个。

添加新批注
在作者公开此批注前,只有你和作者可见。
回复批注