• C#ref和out的区别-ref是有进有出,out是只出不进


    之前学习C#时候就遇到了这个问题,不过当时没有深究。昨晚想到这个问题时候自己尝试敲了敲代码,结果从运行的结果来看,越看越乱。在查看了一些资料的基础上,自己总结了一下。
    可能会有点乱,但是自己总结出来的东西。
     
    一:ref 关键字使参数按引用传递。
    其效果是,当控制权传递回调用方法时,在方法中对参数所做的任何更改都将反映在该变量中。若要使用 ref 参数,则方法定义和调用方法都必须显式使用 ref 关键字。
    也即是说,在方法中对参数的设置和改变将会直接影响函数调用之处(代码①及②)。无论是函数的定义还是调用时均不可忽略关键字ref.
    可以对比代码:
    代码①:
    复制代码
     1 class Program
     2     {
     3         static void Main(string[] args)
     4         {
     5             Program pg = new Program();
     6             int x = 10;
     7             int y = 20;
     8             pg.GetValue(ref x, ref  y);
     9             Console.WriteLine("x={0},y={1}", x, y);
    10 
    11             Console.ReadLine();
    12           
    13         }
    14 
    15         public void GetValue(ref int x, ref int y)
    16         {
    17             x = 521;
    18             y = 520;
    19         }
    20     }
    复制代码
    运行结果为

    代码②:

    复制代码
     1 class Program
     2     {
     3         static void Main(string[] args)
     4         {
     5             Program pg = new Program();
     6             int x = 10;
     7             int y = 20;
     8             pg.GetValue(ref x, ref  y);
     9             Console.WriteLine("x={0},y={1}", x, y);
    10 
    11             Console.ReadLine();
    12           
    13         }
    14 
    15         public void GetValue(ref int x, ref int y)
    16         {
    17             x = 1000;
    18             y = 1;
    19         }
    20     }
    复制代码

    由代码① 和②的运行结果可以看出,在方法中对参数所做的任何更改都将反映在该变量中,而在main函数中对参数的赋值却没有起到作用,这是不是说明不需要进行初始化呢?来看第二点

    二:ref定义的参数在使用前必须初始化,无论在函数定义时候参数有没有赋予初值。这条正好区分out指定的参数可以不在调用函数的时候进行初始化。
    来看代码③ 以及其运行结果:
    复制代码
     1  class Program
     2     {
     3         static void Main(string[] args)
     4         {
     5             Program pg = new Program();
     6             int x;
     7             int y;        //此处x,y没有进行初始化,则编译不通过。
     8             pg.GetValue(ref x, ref  y);
     9             Console.WriteLine("x={0},y={1}", x, y);
    10 
    11             Console.ReadLine();
    12           
    13         }
    14 
    15         public void GetValue(ref int x, ref int y)
    16         {
    17             x = 1000;
    18             y = 1;
    19         }    
    20     }
    复制代码

    出现的错误为:使用了未赋值的局部变量“x”,“y”。故可以说明ref指定的参数无论在函数定义的时候有没有赋予初值,在使用的时候必须初始化。

    三 :对out来说,第一条同样适用。将代码①以及②中的ref全部修改成out,则可与使用ref得到同样的结果。
     
    四:out指定的参数必须在函数定义的时候就赋初值。否则则出现错误。对比ref指定的参数则可以不在函数内部进行赋初值,在函数调用时候再赋初值也可以。
    代码④:
    复制代码
     1 class Program
     2     {
     3         static void Main(string[] args)
     4         {
     5             Program pg = new Program();
     6             int x=10;
     7             int y=233;
     8             pg.Swap(out x, out y);
     9             Console.WriteLine("x={0},y={1}", x, y);
    10 
    11             Console.ReadLine();
    12           
    13         }
    14 
    15         public void Swap(out int a,out  int b)
    16         {
    17             
    18             int temp = a;   //a,b在函数内部没有赋初值,则出现错误。
    19             a = b;
    20             b = temp;
    21         }     
    22     
    23     }
    复制代码
    出现错误:使用了未赋值的out参数“a”,"b"
    则在swap函数定义时候给a,b赋上初值则运行正确。
     
    总结以上四条得到ref和out使用时的区别是:
    ①:ref指定的参数在函数调用时候必须初始化,不能为空的引用。而out指定的参数在函数调用时候可以不初始化;
    ②:out指定的参数在进入函数时会清空自己,必须在函数内部赋初值。而ref指定的参数不需要。
  • 相关阅读:
    条件随机场(crf)及tensorflow代码实例
    Adam作者大革新, 联合Hinton等人推出全新优化方法Lookahead
    33.服务之间的调用之RPC、Restful深入理解
    RPC框架调用过程详解
    Spring 面试问题 TOP 50
    myBatis+Spring+SpringMVC框架面试题整理
    JavaSSM框架精选50道面试题
    maven build的常用生命周期
    玄武短信接口和移动MAS短信接口的API封装
    Java异步执行多个HTTP请求的例子(需要apache http类库)
  • 原文地址:https://www.cnblogs.com/sdya/p/4431837.html
Copyright © 2020-2023  润新知