zoukankan      html  css  js  c++  java
  • C# 7 新特性-1

    来源https://www.kenneth-truyers.net/2016/01/20/new-features-in-c-sharp-7/

    Tuples##

    What###

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

    Why###

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

    Out 参数###

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

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

    Tuple-type####

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

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

    class/struct####

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

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

    How###

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

    Tuple return types####

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

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

    内联tuples####

    可以如下创建tuples

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

    tuple解构####

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

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

    Record类型##

    是什么###

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

    为什么###

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

    class MyPoint
    {
        int _x;
        int _y;
        int _z;
        MyPoint(int x, int y, int z){
            this._x = x;
            this._y = y;
            this._z = z;
        }
        public int X {get{ return this._x;}}
        public int Y {get{ return this._y;}}
        public int Z {get{ return this._z;}}
    }
    

    How###

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

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

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

    模式匹配##

    是什么###

    有了record类型,我们能使用内置的模式匹配。模式匹配意味着你可以在switch语句中根据你所获得数据的类型来执行一个或者其他的语句(也就是跳转到不同分支上)。

    为什么###

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

    How###

    模式匹配如下

    class Geometry();
    class Triangle(int Width, int Height, int Base) : Geometry;
    class Rectangle(int Width, int Height) : Geometry;
    class Square(int width) : Geometry;
     
    Geometry g = new Square(5);
    switch (g)
    {
        case Triangle(int Width, int Height, int Base):
            WriteLine($"{Width} {Height} {Base}");
            break;
        case Rectangle(int Width, int Height):
            WriteLine($"{Width} {Height}");
            break;
        case Square(int Width):
            WriteLine($"{Width}");
            break;
        default:
            WriteLine("<other>");
            break;
    }
    

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

    结论##

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

  • 相关阅读:
    centos7系统中忘记了root管理员账号密码的解决方式
    【python之路48】生成器表达式、推导式
    小米集团信息化中台战略
    分时函数
    函数节流
    JS浮点计算问题
    要转型做前端开发了
    优秀的开发人员和测试人员应有的态度
    C#数组的笔记
    LINQ不包含列表
  • 原文地址:https://www.cnblogs.com/yanbinliu/p/5205748.html
Copyright © 2011-2022 走看看