zoukankan      html  css  js  c++  java
  • 2017-07-26关于set和get访问器以及value的理解

     1     class TestA
     2     {
     3         private int? app;//这是字段
     4         public int APP//这是属性
     5         {
     6             get//get和set类似于一种函数,原本是为访问一个类的私有成语服务的
     7             {
     8                 int tempApp = app * 10 ?? 1;
     9                 return tempApp;
    10             }
    11             set
    12             {
    13                 app = value;
    14             }
    15         }
    16 
    17 
    18         private int obs;
    19         public int OBS
    20         {
    21             get
    22             {
    23                 return obs;
    24             }
    25             set//这里旨在说明无论是get还是set都可以含有逻辑处理
    26             {
    27                 //value是传过来的值,上面也说过get和set类似于一个函数
    28                 //那么“demo.OBS = -10”可以理解成形参是value,这是被赋予了-10这个数字,调用“set函数”
    29                 if (value < 0)
    30                 {
    31                     obs = value * -1;
    32                 }
    33                 else
    34                 {
    35                     obs = value;
    36                 }
    37             }
    38         }
    39     }
    40 
    41     class Program
    42     {
    43         static void Main(string[] args)
    44         {
    45             TestA demo = new TestA();
    46             Console.WriteLine("一开始demo.APP为空,调用get后的判空逻辑后为:{0}", demo.APP);
    47             demo.APP = 10;
    48             Console.WriteLine("赋值语句:demo.APP = 10,调用set。。。。
    " +
    49                 "              此时私有成员demo.app的值为10;");
    50             Console.WriteLine("上面已经为demo.APP赋值,实际是对demo.app赋值,此时调用get后的乘10逻辑为:{0}", demo.APP);
    51 
    52             Console.WriteLine("
    ==================华丽的分割线===================
    ");
    53 
    54             Console.WriteLine("这里调用demo.OBS的get,应该是int的默认值:{0}", demo.OBS);
    55             demo.OBS = -10;
    56             Console.WriteLine("赋值语句:demo.OBS = -10,调用set。。。。。。
    " +
    57                 "              此时私有成员demo.app的值已经是10;");
    58             Console.WriteLine("经过上面的赋值,此时的demo.OBS为:{0}", demo.OBS);
    59             Console.ReadKey();
    60         }
    61     }

    额,本来想先写这段说明的,奈何弄了代码后无法把代码块下调,就只好写在代码后了~

    C#入门的书看了不少,属性和字段的区别理解了很久感觉还是没底,我个人的理解是属性会带上访问器,而字段和C++类中的属性是一个意思。那为什么C#会字段属性不同呢?我理解的原因是,用C++举例子,属性的访问权限往往都是私有的,如果我们要访问它们,通常的做法是写对应的SetXxx()和GetXxx()函数,这会很麻烦,因此C#就有了这个语法糖(我姑且当它是语法糖了,不知道这么理解会不会有偏差)。关于这方面的只是,我觉得应该是不难,只是可能我还没有跳出C++固有的限制,所以心里老觉得怪怪的,也无心吸收书中的知识。欢迎大家指正和赐教,本文不是探讨这个问题。说说另一个这方面困扰我的一个问题,那就是set访问器中的value是什么鬼。

    很多书上介绍set和get往往都是从它的历史演变介绍,典型的就是

    private int _tra;
    public int Tra
    {
            get
            {
                return _tra;
            }
            set
            {
                tra = value;
            }
    }
    

    然后慢慢地演变成连private字段都没有了,直接一个public并且get和set直接public int Tra{get; set;},其实这样会让新人感到一头雾水,究竟这个set和get有何用,毕竟都已经是public了,可以直接存取了,何必写get和set呢?

    再者,我一直的惯性思维是重写get访问器的多,set的少(书上的例子数量也就是给人这样的感觉),所以这个value有什么用?set里究竟能不能写逻辑?

    其实根本是要弄清楚get和set的作用,就拿这个_tra做例子:

    get顾名思义就是得到,也就是“取”,取出这个值的意思。那么什么时候需要取出这个值?当然就是这个属性作为表达式的右值,例如a = Tra,这样a要想得到值,是不是应该取出Tra这个值然后赋给a呢。相反的set就是设置,也就是给这个属性赋值,那它当然是作为表达式的左值了,例如Tra = a。

    用函数的思维去想这个事情,我们假设set和get就是函数,get函数通过名字我们第一反应应该是“得到什么”的意思,因此这个函数里是不是应该有一句return呢?而set函数是设置什么的意思,那么是不是应该传个参数让它知道设成什么呢?这就是value的作用。

    其实不要脱离当初发明set和get的原因去想这件事,我之所以比喻成函数是因为以往在C++我们就是要写SetXxx()和GetXxx()函数访问私有成员,而GetXxx()函数确实肯定有返回值,SetXxx()一般都有参数,这就是get和set访问器的雏形嘛。只不过因为要好看,而且大多时候SetXxx()也就传递一个参数而已,因此C#为了简洁美和方便使用,就搞了一个value的关键字,其实相当于SetXxx()函数的参数。这个value和形参一样都共同的特点就是不会改变,不影响调用方。实际上我们也不会去修改value的值(但它是允许被修改的)

    下面是开始代码的运行结果~

    运行结果

    观看value究竟是什么鬼,我在第29行设置了一个断点进行调试,可以理解成就是一个形参。只不过函数调用的方法和真正的函数调用不太一样。

    插入断点窥探value

    关于正式的说明,可以参考官方文档:https://docs.microsoft.com/zh-cn/dotnet/csharp/language-reference/keywords/value

  • 相关阅读:
    js库链接
    小程序实现textarea行数自动增加
    小程序中公告消息自动向左滚动(关闭三次之后不再提示公告信息)
    jQuery实现点击div外的区域,来隐藏指定节点
    Unity AssetBundle爬坑手记
    换装demo随手记
    Untiy PoolManager随手记
    unity常用插件
    Untiy一些方法前特殊标签记录
    Unity网格合并_材质合并
  • 原文地址:https://www.cnblogs.com/LittleSec/p/7242697.html
Copyright © 2011-2022 走看看