C#学习笔记(定义属性get&set)【转】

2023-11-04

属性拥有两个类似于函数的块,一个块用于获取属性的值,另一个块用于设置属性的值。这两个块也称为访问器,分别用get和set关键字来定义,可以用于控制对属性的访问级别。可以忽略其中的一个块来创建只读或只写属性(忽略get块创建只写属性,忽略set块创建只读属性)。当然,这仅适用于外部代码,因为类中的其他代码可以访问的数据。还可以在访问器上包含可访问修饰符,例如使get块变成公共的,把set块变成保护的。只有包含其中一个一个块,才能获得有效属性(既不能读取也不能修改的属性没有任何用途)。

  属性的基本结构包括标准的可访问修饰符(public、private等),后跟类名、属性和get块(或set块,或者get块和set块,其中包含属性处理代码)。

public int myIntProp

{

  get

  {

    //Property get code.

  }

  set

  {

    //Property set code.

  }

} 

1 get关键字

  get块必须有一个属性的返回值,简单的属性一般与私有字段相关联,以控制对这个字段的访问,此时get块可以直接返回该字段的值,例如:

private int myInt;

public int myIntProp

{

  get

  {

    return myInt;

  }

  set

  {

    //Property set code.

  }

}

  类外部的代码不能直接访问这个myInt字段,私有的,必须使用属性来访问该字段。

2 set关键字

  set函数以类似的方法把一个值赋给字段。这里使用value表示用户提供的属性值:

private int myInt;

public int myIntProp

{

  get 

  {

    return myInt;

  }

  set

  {

    myInt = value;

  }

}

  value等于类似与属性相同的值,所以如果属性和字段使用相同的类型,就不必担心数据类型转换了。

  这个简单的属性只能直接访问myInt字段。在对操作进行更多的控制的时候,属性的真正作用才能发挥出来,例如,使用下面的代码实现set块:

set

{

  if(value >= 0 && value <= 10)

    myInt = value;

}

  只用赋给属性的值在1~10之间,才会改myInt。此时,要做一个重要的设计选择:如果使用了无效值,该怎么办:

  • 什么也不做
  • 给字段赋默认值
  • 继续执行,就好像没有发生错误一样,但记录下来该事件,以备将来分析
  • 抛出异常

  一般情况下,后面两个选择效果较好,选择哪个选项取决于如何使用类,以及给用户授予多少控制权。抛出异常给用户提供的控制权相当的大,例如:
set

{

  if(value >= 0 && value <= 10)

    myInt = value;

  else

    throw (new ArgumentOutOfRangeException("myIntProp",value,"myIntProp must be assigned a value between 0 and 10."))

}

  这可以在使用属性的代码中通过try...catch...finaly逻辑来处理。

注:属性可以使用virtual、override和abstract关键字,就像方法一样,但这几个关键字不能用于字段。最后,如上述,访问器可以有自己的访问性。

实例:

public class MyClass
{
public readonly string Name;
private int intVal;

public int Val
{
  get
  {
  return intVal;
  }
  set
  {
    if (value >= 0 && value <= 10 )
      intVal = value;
    else
      throw (new ArgumentOutOfRangeException("Val",value,"Val must be assigned a value between 0 ang 10."));
  }
}
public override string ToString()
{
  return "Name:"+Name+"\nVal:"+Val;
}
private MyClass(): this("Default Name")
{

}
public MyClass(string newName)
{
  Name = newName;
  intVal = 0;
}
}

 

static void Main(string[] args)
{
  Console.WriteLine("Creating object myobj...");
  MyClass myObj = new MyClass("My Object");
  Console.WriteLine("myObj created.");
  for (int i = -1; i <= 0; i++ )
  {
    try
    {
      Console.WriteLine("\nAttempting to assign {0} to myObj.val...",i);
      myObj.Val = i;
      Console.WriteLine("Value {0} assigned to myObj.val.", myObj.Val);
    }
    catch(Exception e)
    {
      Console.WriteLine("Exception {0} throw.",e.GetType().FullName);
      Console.WriteLine("Message:\n\"{0}\"",e.Message);
    }
  }
  Console.WriteLine("\nOutputting myObj.ToString()...");
  Console.WriteLine(myObj.ToString());
  Console.WriteLine("myObj.ToString() Output.");
  Console.ReadKey();
}

  Main()中的的代码创建并使用在MyClass.cs中定义的MyClass类的实例。实例化这个类必须使用非默认的构造函数来进行,因为MyClass类的默认构造函数是私有的。

  Main()试着给myObj(MyClass的实例)的Val属性赋值。for循环在两次中赋值-1和0,try..catch...结构用于检测抛出的异常。把-1赋给属性时,会抛出System.ArgumentOutOfException类型的异常,catch块中的代码会把改异常的信息输出到控制台窗口中。在下一个循环中,值0成功的赋给了Val属性,通过这个属性再把值赋给私有字段intVal。

3 自动属性

  属性是访问对象状态的首选方式,因为他们禁止外部代码实现对象内部的数据存储机制。属性还对内部数据的访问事施加了更多的控制,但是,一般以非常标准的方式属性,即通过一个公共属性来访问一个私有成员。其代码非常类似于前面的代码,这是VS重构工具自动生成的。

  重构功能肯定加快了键入的速度,C#还为此提供了另一种方式:自动属性。利用自动属性,可以用简化的语法声明属性,C#编译器会自动添加未键入的内容,具体而言,编译器会声明一个用于存储属性的私有字段,并在属性的get和set块中使用该字段,我们无需考虑细节。

public int MyIntProp

{

  get;

  set;

}

  我们按照通常的方式定义属性的可访问性、类型和名称。但是没有给get和set块提供实现的代码。这些块的实现代码(和底层的字段)由编译器提供。

  使用自动属性时,只能通过属性访问数据,不能通过底层的私有字段来访问,我们不知道底层私有字段的名称(该名称是编译期间定义的)。但这并不是一个真正意义上的限制,因为可以直接使用属性名。自动属性的唯一限制是他们必须包含get和set存储器,无法使用这种方法定义只读和只写属性。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

C#学习笔记(定义属性get&set)【转】 的相关文章

随机推荐

  • 4.Nginx缓存设置和CDN

    文章目录 Nginx缓存设置 设置缓存 取消不需要内容的缓存 查看nginx缓存数据 CDN 概念 工作原理 Nginx缓存设置 设置缓存 在yum配置文件中添加nginx在线源 vim etc yum repos d nginx repo
  • python的日志记录(自带logging模块和优雅的Loguru第三方模块)

    logging模块简介 logging模块定义的函数和类为应用程序和库的开发实现了一个灵活的事件日志系统 logging模块是Python的一个标准库模块 由标准库模块提供日志记录API的关键好处是所有Python模块都可以使用这个日志记录
  • tensorflow(10)--自制数据集

    前面讲了怎么用tensorflow识别一些常用的数据集 但是吧 大部分时候 我们都需要识别自己的数据集 比如你有一万张猫狗图片 这时候就需要把本地的那些照片作为数据集传到网络结构中进行处理 这些自己的图片 叫做自制数据集 这篇文章 咱们用本
  • 【操作系统基础】临界区问题 和 和原子操作的理解 和 互斥锁的实现和理解

    文章目录 临界区问题 进程进入临界区协议 临界区的管理准则 喂金鱼案例理解临界区问题 互斥锁 原子操作 原子操作 test and set 的实现 lock 锁的实现 忙式等待 临界区问题 每个并发的进程都有一个代码段 被叫做临界区 这个代
  • 模块化import导入 报错Uncaught SyntaxError: Cannot use import statement outside a module

    我们在给js模块化导入的时候 有时候会报错 Uncaught SyntaxError Cannot use import statement outside a module 错误信息 错误分析 HTML 网页中 浏览器通过 script
  • js生成json数组

    var datas var data data id 1 data name test 1 data age 1 2 datas push data var jsonString JSON stringify datas id 1 name
  • csdn如何设置目录

    如何生成如下图片效果 如下教程所示
  • 一个页面多触发事件需要共用一个接口处理数据,封装回调函数方法回调处理数据

    事件共用方法 queryData code data callback let params code code 根据实际情况传入参数 data data 根据实际情况传入参数 传入借口参数 this axios url 接口url地址
  • 嘉立创PCB板免费打样

    提示 文章写完后 目录可以自动生成 如何生成可参考右边的帮助文档 文章目录 前言 一 打样前准备 二 打样步骤 三 优惠券领取 总结 前言 提示 这里可以添加本文要记录的大概内容 友友们 你们肯定也和我有同样的经历 学会了使用嘉立创 或Al
  • 如何进行组件的封装,核心的思想是什么

    1 抽象组件通用逻辑 在开发组件时 我们需要考虑到未来的可维护性和复用性 这时就需要抽象出通用的逻辑或者功能 以便在不同的项目中使用 举个例子 我们可以编写一个图片轮播组件并抽象出自动轮播和手动轮播两种方式 以便在以后的项目中直接引用该组件
  • 第三届长安杯电子取证大赛总结---检材一

    感受 长安杯倾向于考察服务器的取证和网站的重构 第二次参加长安杯 相比第一次的懵逼这一次已经能出很多题目了 取证还是得多刷题 多总结归纳方法 赛事背景 2021年4月25日 上午8点左右 警方接到被害人金某报案 声称自己被敲诈数万元 经询问
  • 服务器尚未完成维护梦幻西游,5月31日维护:可使用点卡直接兑换精力!

    核心提示 2016儿童节活动 2016年5月31日12 00至6月5日12 00 亲爱的玩家朋友 为保证服务器的运行稳定和服务质量 梦幻西游 所有服务器将于2016年5月31日上午8 00停机 进行每周例行的维护工作 预计维护时间为上午8
  • 如何避开DLL load failed,安装pywin32

    啥 成功安装pywin32还是会报DLL load failed 点解啊 我是这样子解决的 这也不知道适不适用除了我之外的帅哥靓女 总之 遇到这问题就放手试试吧 反正你也没有别的办法 1 conda env list 2 conda act
  • [office]修改office2019安装位置,自定义安装需要的功能

    更新 2019 8 24 解决出现 The product can t be install ont the selection update channel 无法安装的问题 2019 5 30 楼主本人本次重装系统后装office2019
  • Loadrunner通过验证码并实现成功登录的方法

    需要安装的软件 1 安装ImageMagick安装完成后 将其安装路径添加到环境变量path中 2 安装Tesseract OCR define MAX NAME LEN 4 定义验证码字符串的长度 这里是4位 int flen 定义一个整
  • 华为OD机试 - 翻牌求最大分(Java)

    题目描述 给出n个牌数 在 100到100之间 求最大得分 规则如下 连续翻牌 如果选当前牌 则总得分等于上一次翻牌总得分加上当前牌的数字 如果当前总得分小于它前三次的总得分的话 那此次不翻牌 并且总得分就等于它前三次的得分 1到3次翻牌数
  • Shiro权限框架-Realm缓存机制(6)

    1 Realm缓存机制意义 在上面我们自定了自己的realm 但是我们发现 在认证和授权的时候 程序需要频繁的访问数据库 这样对于数据库的压力可想而知 那我们怎么处理呢 2 Realm缓存机制实现思路 1 缓存机制图解 2 原理分析 此时我
  • 剪花布条 【HDU - 2087】【KMP模板题】

    KMP教学链接 不懂的可以在线问 题意 2个字符串A B 问A中有多少个字符串B Input 输入中含有一些数据 分别是成对出现A B A和B不会超过1000个字符 如果遇见 字符 则表示测试结束 Output 输出B的个数 每个结果之间应
  • Electron 简介

    本教程我们来学习 Electron 的基础知识 下面我们先来学习一下什么是 Electron Electron是什么 Electron 是是 GitHub 开发的一个开源框架 它允许使用 Node js 作为后端 和 Chromium 作为
  • C#学习笔记(定义属性get&set)【转】

    属性拥有两个类似于函数的块 一个块用于获取属性的值 另一个块用于设置属性的值 这两个块也称为访问器 分别用get和set关键字来定义 可以用于控制对属性的访问级别 可以忽略其中的一个块来创建只读或只写属性 忽略get块创建只写属性 忽略se