字段(Field)与属性(Property)
C#方法,属性,字段
C#⽅法,属性,字段以前是学C++的,初次学微软的C#头都⼤了。
什么字段,常量,属性,⽅法......微软把别⼈的东西拿来糅合在C#⾥,弄成了⼀个“⼤杂烩”。
其实,说到底,“字段”不就是“变量”吗,所谓的“⽅法”不就是“函数”吗,故弄⽞虚!从MSDN上弄来了详细的介绍,看下⾯::字段字段:“字段”是直接在或中声明的任何类型的变量。
字段是其包含类型的“成员”。
类或结构可以拥有实例字段或静态字段,或同时拥有两者。
实例字段特定于类型的实例。
如果您拥有类 T 和实例字段 F,可以创建类型 T 的两个对象,并修改每个对象中 F 的值,这不影响另⼀对象中的该值。
相⽐之下,静态字段属于类本⾝,在该类的所有实例中共享。
从实例 A 所做的更改将⽴刻呈现在实例 B 和 C 上(如果它们访问该字段)。
通常应仅为具有私有或受保护可访问性的变量使⽤字段。
您的类向客户端代码公开的数据应通过、和提供。
通过使⽤这些构造间接访问内部字段,可以针对⽆效的输⼊值提供防护。
存储由公共属性公开的数据的私有字段称为“后备存储”或“⽀持字段”。
字段通常存储这样的数据:该数据必须可供多个类⽅法访问,并且其存储期必须长于任何单个⽅法的⽣存期。
例如,表⽰⽇历⽇期的类可能有三个整数字段:⼀个表⽰⽉份,⼀个表⽰⽇期,还有⼀个表⽰年份。
不在单个⽅法范围外部使⽤的变量应在⽅法体⾃⾝范围内声明为局部变量。
在类块中通过指定字段的访问级别,然后指定字段的类型,再指定字段的名称来声明这些字段。
例如:1 public class CalendarEntry2 {3 // private field4 private DateTime date;56 // public field (Generally not recommended.)7 public string day;89 // Public property exposes date field safely.10 public DateTime Date11 {12 get13 {14 return date;15 }16 set17 {18 // Set some reasonable boundaries for likely birth dates.19 if (value.Year > 1900 && value.Year <= DateTime.Today.Year)20 {21 date = value;22 }23 else24 throw new ArgumentOutOfRangeException();25 }2627 }2829 // Public method also exposes date field safely.30 // Example call: birthday.SetDate("1975, 6, 30");31 public void SetDate(string dateString)32 {33 DateTime dt = Convert.ToDateTime(dateString);3435 // Set some reasonable boundaries for likely birth dates.36 if (dt.Year > 1900 && dt.Year <= DateTime.Today.Year)37 {38 date = dt;39 }40 else41 throw new ArgumentOutOfRangeException();42 }4344 public TimeSpan GetTimeSpan(string dateString)45 {46 DateTime dt = Convert.ToDateTime(dateString);4748 if (dt != null && dt.Ticks < date.Ticks)49 {50 return date - dt;51 }52 else53 throw new ArgumentOutOfRangeException();5455 }56 }若要访问对象中的字段,请在对象名称后⾯添加⼀个句点,然后添加该字段的名称,⽐如 objectname.fieldname。
C#属性(Property)和字段(Field)的区别
C#属性(Property)和字段(Field)的区别导读:近期学习过程中发现了⼀些问题,我的学习只是学习,敲代码就是敲代码,没有加⼊思考,也不问为什么就直接去敲⼈家写好的例⼦去敲,把知识都学死了,逐渐散失了思考能⼒,所以学习的兴趣⼤打折扣,正如那句话—学⽽不思则罔,思⽽不学则殆,在设计模式中偶然看到了属性和字段,想想之前的C#中也提到过,但是从来没有思索过为什么有属性和字段?下⾯就来详细说明。
【字段】字段(Field)是⼀种表⽰与对象或类关联的变量的成员,字段声明⽤于引⼊⼀个或多个给定类型的字段。
字段是类内部⽤的,private类型的变量(字段),通常字段写法都是加个"_"符号,然后声明只读属性,字段⽤来储存数据。
【属性】属性(Property)是另⼀种类型的类成员,定义属性的⽬的是在于便于⼀些私有字段的访问。
类提供给外部调⽤时⽤的可以设置或读取⼀个值,属性则是对字段的封装,将字段和访问⾃⼰字段的⽅法组合在⼀起,提供灵活的机制来读取、编写或计算私有字段的值。
属性有⾃⼰的名称,并且包含get 访问器和set 访问器。
声明格式:属性修饰符类型属性名{get{//get访问器代码}set{//set访问器代码}}属性分类:根据get访问器和set访问器是否存在,属性可按下列规则分类。
那么问题来了,既然已经有字段⽤来存储数据,为什么还要引⼊属性来对数据进⾏访问,把声明的字段直接定义成公有的不就可以了吗?解答:在C#中,我们可以⾮常⾃由的、毫⽆限制的访问公有字段,但在⼀些场合中,我们可能希望限制只能给字段赋于某个范围的值、或是要求字段只能读或只能写,或是在改变字段时能改变对象的其他⼀些状态,这些单靠字段是⽆法做到的,于是就有了属性,属性中包含两个块:set和get,set块负责属性的写⼊⼯作,get块负责属性的读取⼯作。
在两个块中都可以做⼀些其他操作,如在set中验证赋的值是否符合要求并决定是否进⾏赋值。
C#字段(field),属性(property)
C#字段(field),属性(property)C#字段和属性: 类成员包括变量和⽅法。
如果希望其他类能够访问成员变量的值,就必须定义为公有的,⽽将变量设为公有public,那这个成员变量就可以被任意访问(包括修改和删除),这样不利于数据安全。
C#通过属性读取和写⼊字段(成员变量),⽽不直接读取和写⼊,以此来提供对类中字段的保护。
属性可以⽤于类内部封装字段,属性是C#⾯向对象技术中封装性的体现。
属性和字段的区别: 属性是逻辑字段,是字段的扩展,并不占⽤实际的内存;⽽字段占⽤内存空间。
属性可以被其他类访问,⽽⾮public的字段不能被直接访问。
属性可以对接受的数据在范围上做限定;⽽字段不能。
使⽤属性的情况: 要求字段只能读或者写。
要求限制字段的取值范围。
在改变⼀个字段的值的时候希望改变对象的其他⼀些状态。
使⽤字段的情况: 允许⾃由读写。
取值范围只受数据类型约束⽽⽆其他任何特定限制。
值的变动不需要引发其他成员的相应变化。
using System;using System.Collections.Generic;using System.Linq;using System.Text;namespace ConsoleApplication1{class Person{private string _name;private string _identificationID;private string _phoneNumber;public string Name { get; set; } //可读,可写public string IdentificationID { get; private set; } //只读public string PhoneNumber{get{return _phoneNumber;}set{if (value.Length != 11){Console.WriteLine("⼿机号码应该为11位!");}else{_phoneNumber = value;}}}}class Program{static void Main(string[] args){Person cherry = new Person(); = "Cherry";cherry.PhoneNumber = "12345678910";cherry.IdentificationID = "320000000000000000"; //报错,由于定义的是只读属性}}}。
记java实体类属性名为全部为大写踩的坑(基础)
记java实体类属性名为全部为⼤写踩的坑(基础)1.今天后台使⽤实体类接收参数,然后有个参数发现明明前后都是对应的,但是那个属性偏偏的不到数据后⾯百度才知道(写前端太久java基础都给忘了,该补补了)spring默认的命名⽅式为,⾸字母转⼩写,连续⼤写字母都转成了⼩写恍然⼤悟:也就是说当我实体类⾃动为SN时,get⽅法getSN也就相当于get,sn这个字段,set⽅法getSN也就相当于set,sn这个字段,就会导致跟字段SN不对应,导致⽆法注⼊值这时候其实有解决的办法,就是get,set⽅法添加@JsonPropety("属性名")解决Java的规范是⾸字母⼩写的然后驼峰命名看源码后发现public static String decapitalize(String s){if(s == null || s.length() == 0)//空处理return s;if(s.length() > 1 && Character.isUpperCase(s.charAt(1)) && Character.isUpperCase(s.charAt(0))){//长度⼤于1,并且前两个字符⼤写时,返回原字符串return s;} else{//其他情况下,把原字符串的⾸个字符⼩写处理后返回char ac[] = s.toCharArray();ac[0] = Character.toLowerCase(ac[0]);return new String(ac);}}得出结论当实体类的属性为前两个为⼤写时他会返回原字符AA->AAAa->aaaa->aa这样的差异会导致set,get取不到对应的值,所以还是严格按照java的命名规范来JavaBean 中的属性是通过 get/set ⽅法名得来的,因此getSname 对应的属性名是 snamegetSName 对应的属性名是 SName如果写成 sName 或者 Sname 的话就是不合法的属性名。
C#中字段与属性性能比较
【摘要】【目的】比较字段与属性读取的性能【结论】使用字段比属性赋值,快50-60倍左右,读取,快3倍左右。
但是它不可能成为影响性能的主要瓶颈Effective C# 原则1:尽可能的使用属性(property),而不是数据成员(field)。
把所有的字段都设为私有字段,如果要暴露它们,则把它们封装成属性。
这也是微软推荐的方式。
具体的好处此处不赘述。
属性的实质是方法(get和set方法),IL中没有属性的概念。
因此,使用属性必然会带来性能的降低。
到底使用属性和使用字段的性能差多少。
我自己写了一个小程序进行测试。
主要代码如下:public class TestFeildProperty{static readonly int _RunTime = 10000000;public static void UseField(){DateTime begin = DateTime.Now;int milliSecondBegin = lisecond;for (int i = 0; i < _RunTime; i++){_TestField = 1;}DateTime end = DateTime.Now;TimeSpan result = end - begin;Console.WriteLine(result.ToString());}public static void UseProperty(){DateTime begin = DateTime.Now;int milliSecondBegin = lisecond;for (int i = 0; i < _RunTime; i++){TestField = 1;}DateTime end = DateTime.Now;TimeSpan result = end - begin;Console.WriteLine(result.ToString());}static int _TestField;static int TestField{set { _TestField = value; }get { return _TestField; }}}测试方式为对字段和属性循环赋值和读取(以上代码只有赋值部分)。
field字段
field字段field字段是在计算机科学和信息技术领域中常用的术语。
它用于描述数据结构中的一个单元或属性,用于存储特定类型的数据。
在数据库管理系统和编程语言中,field字段是一个命名的数据项,用于存储特定类型的值。
在关系型数据库中,每个表都由多个字段组成,用于存储表中的不同类型的数据。
每个字段都有一个名称和一个数据类型,例如整数、字符串、日期等。
这些字段可以用于定义表的结构和规范,以及实现数据的有效组织和管理。
例如,一个用户表可能包含字段如:姓名、年龄、性别等。
在编程语言中,field字段通常是指一个类或结构体中的变量或属性。
它可以用来描述对象的不同特征或状态。
例如,一个汽车类可以有颜色、品牌、型号等字段,用于存储不同汽车对象的属性。
通过访问和修改这些字段,可以操作和处理对象的数据。
field字段在数据分析和机器学习领域也非常常见。
在数据集中,每一列通常对应一个字段,表示一个特定的特征。
例如,在一个客户数据集中,字段可以包括年龄、性别、收入等,用于描述不同客户的特征。
通过对这些字段进行分析和挖掘,可以从数据中获取有价值的信息和洞察。
此外,field字段还有其他的应用和扩展。
例如,在网络协议中,field 字段用于描述和传输数据包的不同部分。
在表单和页面设计中,field 字段用于表示用户输入的表单元素和数据。
在电子邮件和文件格式中,field字段用于指定和解析不同的数据段。
总结来说,field字段是用于存储和描述数据的一种标准化方式。
它在不同的领域和应用中都起着重要的作用,用于定义和组织数据的结构和属性。
通过使用field字段,可以更好地管理和操作数据,并从中获得有价值的信息。
C#如何反射获取类中const常量(Static属性字段),并且获取值和设置值
BindingFlags flag = BindingFlags.Static | BindingFlags.NonPublic; FieldInfo f_key = typeof(ClsPublic).GetField("key", flag); f_key.SetValue(new ClsPublic(), key); }
/// <summary> /// 获取key /// </summary> /// <returns></returns> public static string getPalmKey() {
BindingFlags flag gFlags.NonPublic; FieldInfo f_key = typeof(ClsPublic).GetField("key", flag); object o = f_key.GetValue(new ClsPublic()); return o.ToString(); }
flag用于表示static和nonpublic私有类型private的静态staic的字段field或属性propertyconst被隐式的认为是静态属性
C#如何反射获取类中 const常量( Static属性字段),并且获取 值和设置值
//动态链接库中ClsPublic类有一变量 private static string key="1111"; //下面通过反射的技术修改和获取值 //设置key
flag 用于表示 Static 和 NonPublic 私有类型(Private)的 静态(Staic)的 字段(Field) 或 属性(Property) ,Const 被隐式的认为是 静态属性。
变量、字段、域、属性、属性过程
C#中的变量、字段、域、属性、属性过程在C#中:域:表示与对象或类相关联的变量,修饰符不论是不是public。
(与字段类似)字段:表示与对象或类相关联的变量。
通常来讲修饰符是public的成员变量称为字段,而private更适合说是局部变量。
(与域类似)属性:表示域或字段的自然扩展,使得在保证封装性的基础上实现了访问私有成员的便捷性。
域域表示与对象或类相关联的变量,声明格式如下:attributes field-modifiers type variable-declarators;域的修饰符field-modifiers可以是:new、public、protected、internal、private、static、readonly。
实际上,域相当于C++中的简单成员变量。
在下面的代码中,类A包含了三个域:公有的X和Y,以及私有的z。
class A{public int x;public string y;private float z;}字段字段是与对象或类相关联的变量。
当一个字段声明中含有static修饰符时,由该声明引入的字段为静态字段(static field)。
它只标识了一个存储位置。
不管创建了多少个类实例,静态字段都只会有一个副本。
当一个字段声明中不含有static修饰符时,由该声明引入的字段为实例字段(instance field)。
类的每个实例都包含了该类的所有实例字段的一个单独副本。
在下面的示例中,Color类的每个实例都有r,g,b实例字段的不同副本,但是Black,White,Red,Green和Blue等静态字段只有一个副本:public class Color{public static readonly Color Black = new Color(0, 0, 0);public static readonly Color White = new Color(255, 255, 255);public static readonly Color Red = new Color(255, 0, 0);public static readonly Color Green = new Color(0, 255, 0);public static readonly Color Blue = new Color(0, 0, 255);private byte r, g, b;public Color(byte r, byte g, byte b) {this.r = r;this.g = g;this.b = b;}}如示例所示,通过readonly修饰符声明只读字段。
python中field用法
python中field用法在Python中,"field"一词通常用于描述类或数据结构中的成员变量或属性。
在Python中,我们可以使用不同的方法来定义和使用字段。
首先,我们可以使用类来定义字段。
在类中,我们可以使用构造函数`__init__`来初始化字段,例如:python.class Person:def __init__(self, name, age): = name # 定义名为name的字段。
self.age = age # 定义名为age的字段。
在这个例子中,`name`和`age`被称为字段,它们是类的成员变量,可以在类的实例化对象中被访问和修改。
另外,Python还提供了一种称为数据类(dataclass)的特殊装饰器,用于自动创建包含字段的类。
使用数据类,我们可以更简洁地定义带有字段的类,例如:python.from dataclasses import dataclass.@dataclass.class Person:name: str # 定义名为name的字段,类型为str.age: int # 定义名为age的字段,类型为int.在这个例子中,我们使用`dataclass`装饰器来自动创建`Person`类,并定义了`name`和`age`字段。
这样,Python会自动为我们生成`__init__`方法和其他常见方法。
此外,在Python中,我们还可以使用属性(property)来创建字段,属性允许我们在访问或设置字段值时执行特定的逻辑。
例如: python.class Circle:def __init__(self, radius):self._radius = radius # 定义名为_radius的字段。
@property.def radius(self):return self._radius # 定义radius属性来访问_radius字段。
Property和Attribute的区别
C#中Property和Attribute的区别●Property就是访问字段(成员变量,Field)提供的一种方式(set/get)●Property是C#中引入的一种语言特性,把C++中的一些编程技巧上升到语法的地位。
这种特性就是把类数据成员声明为私有的,而提供公有的方法实现对他们的访问。
●Property可以说是一个面向对象的概念,提供了对私有字段的访问封装,在C#中以get和set访问器方法实现对可读可写属性的操作,提供了安全和灵活的数据访问封装。
比如:1.public class Robot2.{3.private string name = ""; //字段:Field4.public string Name //属性:Property,对Field进行封装。
5. {6.get { return name; }7.set { name = value; }8. }9.}●Property是指类向外提供的数据区域,是智能的字段,其中有get和set访问器来完成字段的取值和赋值。
而Attribute则是描述对象在编译时或运行时属性的。
这两者是有本质区别的,一个是属性,用于存取类的字段,一个是特性,用来标识类,方法等的附加性质。
是Attribute,还是Property?Attribute和Property都能翻译成“属性”,有的地方用attribute表示“属性”,有的地方又在用roperty,初学者常常在这两个单词间“迷失”,甚至认为二者没有差别,是相同的。
可是attribute不等于property。
二者之间到底有何差别?我们从OOA/OOD(object oriented analysis / object oriented design,面向对象分析和设计)说起。
在OOA/OOD中的使用attribute表示属性,指对象(object)的特征(feature)。
C#类的成员(字段、属性、方法)
C#类的成员(字段、属性、⽅法)前⾯定义的Person的类,⾥⾯的成员包括:字段、属性、⽅法、事件等,此外,前⾯说的嵌套类也是类的成员。
a.类的成员为分:静态成员(static)和⾮静态成员b.静态成员⽤static标识,不标识则默认为⾮静态成员c.静态成员属于类所有,动态成员则属于实例所有,即对象d.静态成员为类所有实例共享,⽆论类有多少实例或副本,静态成员只占⽤存中⼀块区域。
⾮静态成员则在类的每个实例,都创建⼀个内存域。
下⾯主要说明⼀下类的主要成员:字段、属性、⽅法1.类的成员——字段(field)字段声明:(static/readonly) <Type> <变量名称>a.可以理解为类的⼀个私有变量,通常都是私有的(private)。
b.字段的定义通常以⼩写字母开头或 “_” 开头。
c.字段声明修饰符有static(静态)和readonly(只读)两种。
d字段通常为私有,因此⼀般不需要使⽤访问修饰符.⽰例:1 static int eyesCount=2;2 readonly int earsCount=2;2.类的成员——属性(property)a.可以理解为类的⼀个公有变量,通常都是公有的(public)b.属性有get 和 set 两个⽅法。
c.get 访问器返回与属性声明类型相同的数据,表⽰的意思是调⽤时可以得到内部的字段的值或引⽤。
d.set 访问器没有显⽰设置的参数,它有⼀个隐式参数value 它的作⽤是调⽤时,可以给属性内部字段或引⽤赋值。
e.由于类的成员默认为私有,因为根据属性为公有的特征,在⾯向对象开发过程中,要使⽤修饰符public来声明⼀个属性为公有。
f.属性可以忽略get或set访问器,但是不能两个都忽略.⽰例:1 string _country;2 //读写属性3 public string Country4 {5 set { _country = value; }6 get { return _country; }7 }8 //只读属性9 public string CountryOnleread10 {11 get { return _country; }12 }13 //只写属性14 public string Countryonlywrite15 {16 set { _country = value; }17 }6.类的成员——⽅法(Method )声明:(访问修饰符) <类型> <⽅法名>{⽅法体}调⽤:[<类名.>]|[<实例对象名.>]<⽅法名>([<实参列表>])定义:是类中⽤于执⾏计算或其它⾏为的成员静态⽅法:⽅法分为实例⽅法和静态⽅法(同前⾯讲的类的成员)静态⽅法中只能调⽤静态字段,不允许调⽤⾮静态字段⽅法参数:值参数:不含任何修饰符。
C#属性、自动属性、字段之间的区别和理解
C#属性、⾃动属性、字段之间的区别和理解.ctor是构造⽅法的意思,注意委托其实也是有构造⽅法的(不过是编译器⾃动创建的是私有的)貌似它的参数⼀个是委托引⽤的⽅法所属的对象(或Type对象),⼀个是该⽅法的指针;1.属性的概念其实和字段是有⼀定重合的;C#的属性它不是⽤来表述某个类具有什么样的⾏为,⽽是指某个类具有什么样的成员变量/对象,并且同时指定它可以被外界有什么样的操作;所以按照这个概念其实属性就应该是完全的⾃动属性,⽽不应该再加⼀些其他操作,如果有其他操作应该是字段+⽅法来结合实现;2.属性也可以是静态属性和私有属性,表⽰这个属性是属于某个类的,表⽰这个属性虽然对外提供get或set,但是只是对本类内这个外部范围,不对类外这个外部范围(外部概念可⼤可⼩);3.然后对于抽象编程⾥,某个接⼝具有getXx();的⽅法签名它虽然是getXx()但是它是属于⾏为层⾯的,表⽰它的⼦类具有获得Xx的⾏为;这个Xx可以是字段也可以是属性(这⾥就是它们重合的地⽅);它就是对于JavaBean⾥的具有getter和setter⽅法的字段,它的get,set不是代表这个类具有什么⾏为,⽽是代表这个属性具有什么⾏为;⽽⼀个类实现接⼝是指这个类有什么⾏为,它显然和属性的get,set是不⼀样的,⽐如可以说某个类具有获取属性的⾏为,那么⼦类实现时返回的就是⼀个字段,因为通过属性的get其实也是返回⼀个字段;4.属性它本质上是⼀个私有字段加两个⽅法组成【4.5⾃动属性出现后这个私有字段仍然存在只不过它应该叫unreachable string _name,然后public string Name {get;set;},这个字段只有该属性能访问反射也弄不出来,类似函数⾥的局部变量只有该函数能访问】,⾃动属性的这个私有字段.Net对它做了进⼀步的隐藏,使得只能通过编译器为属性Name⾃动创建的两个⽅法get_Name和set_Name来操作(不信可以去试⼀下,定义了Name属性且get set后这两个⽅法不能⼿动创建),这⾥之所以要弄成这种很不合标准的⽅法,其实就是为了和常⽤标准区别开来,防⽌⽤户本⾝还需要有个GetName⽅法,然后它可能⽤下划线get_name或Get_Name,⽽get_Name正好和这些都不⼀样是偏僻的⽅法,只有⽤户故意捣乱才会这样⼦写;这样的命名不是为了适应⽼版本⾥private string _name的命名风格,就是为了特殊化使得尽可能不和⽤户可能⽤到的命名⽅式⼀样⽽导致⽅法签名重名;这两个⽅法分别对应get和set,如果只有get那么只会⽣成get_Name⽅法;注意,如果不是⾃动属性,那么是编译器能够感知到的从⽽不会为该类(该Type)分配⼀个unreachable字段;反射⾥的成员就类似⼀个和get_Name和set_Name⽅法的桥接对象,是⽤来提供给反射操作属性时和平时编码的⼀致体验,否则我们要在反射⾥实现 = "mm";就必须获得set_Name(..)⽅法来操作,这就和平时写代码的感觉是不⼀致的(也类似Java⾥将泛型setXx<T>()⽅法桥接到setXx()⽅法⾥),⽽有了Name这个反射属性作为桥接⽅法(桥接对象?)【桥接其实就类似转发】,我们就可以直接操作Name来⾃动桥接到set_Name等⽅法⾥;5.对于为属性Name⾃动⽣成的两个⽅法set_Name和get_Name只是反射的时候能看到,但是调试的时候是没法进⼊的,也没法watch到,因此没法通过调试来看get_Name⽅法到底是怎么操作那个unreachable访问权限字段的;⽽虽然反射可以看到这两个⽅法,但是如果要改属性值还是通过属性去改⽐较好(这个对这个属性执⾏写操作会链接到set_Name⽅法上),这样其实也⽅便框架获取可序列化的成员;6.总结(类的组件⽤Property,类的或类属性的描述参数⽤Field):字段和属性都是⽤来描述对象的组成,但是对于那种标准JavaBean(Model层,最多只是实现了ISerializable接⼝)的空间结构组成要⽤属性;⽽对于那种⼯具类、服务类的Bean的空间结构组成⽤字段,除⾮该服务实现类⾥有某个具有JavaBean特质的空间结构,这个时候⽤属性;7.这⾥再来进⼀步区分字段和属性的概念,⽐如⼈这个实例类,⼈有⼝、⿐⼦、眼睛、腿、⼿;然后⼈具有各种动作,⽐如跑步,然后跑步它有快慢,加上 people1这个对象它的跑步速度是10,然后⽤这个例⼦来讲解属性和字段的区分点:⼝、腿、⼿之列的是⼈⾝上的组件,因此是Property,⽽runSpeed是⽤来描述这个⼈的跑步速度,肯定也是存储在这个⼈对象⾥的(每个⼈跑步速度不⼀样),但是它不是⼀种组件,所以它⽤Field来表⽰;还有其他的⼀些数据也是⽤字段,如腿多长,这个就是⽤字段,并且这个可以做成抽象,表⽰某些类具有可以设置腿多长的⾏为;设置跑多快的⾏为;这种听起来还是挺符合⼈类思维的;⽽如果我们说某个动物类具有可以设置眼睛的⾏为,这就感觉怪怪的,因为眼睛它是实体上的⼀个组件⽽⾮参数;再举个例⼦,杯⼦,杯⼦它有杯⾝和背盖(有的可能还有该类杯⼦特定的勺⼦),这些都是组件,⽤Property,但是它还有⼀些描述性的数据(总算想到⼀个⽐较贴切的词),如这个杯⼦能装多少⽔,这个就是描述信息;如果是⾮⾃动属性,那么调⽤Name的反射设置值的时候然后间接调⽤set_Name这⾥会传两个参数,⼀个是this,⼀个是外部参数,然后set_Name将外部参数赋值到this所处的指针加上要赋值对象的在该对象的内存index上即可,⽽⾃动属性其实也是这样⼦赋值的,只不过⾃动属性的赋值的时候set_Name只知道要对this + index来赋值,⽽对⾮⾃动属性它还能知道index对应this 字段的名字是什么(⼀个只知道相对this对象起始位置的偏移量,⼀个不但知道偏移量还知道偏移到那个位置是this⾥哪个字段的起点);或者说⼀个是没有命名的对象内部的某块空间,⼀个是有命名的对象的某块空间,显然没有命名的⽅式是更加精简内存的,否则肯定还需要⼀些地⽅⽤来描述this⾥每个位置的字段名是什么(类似磁盘⾥的卷头,⽤来存储有多少卷,然后每⼀卷的起始位置是哪⾥,每⼀卷的结束位置是哪⾥,每⼀卷的命名是什么,这⾥的磁盘就是对象,每⼀卷起始就是字段,unreachable的字段是没有卷名的,甚⾄在卷头⾥也没有偏移量,这些相对磁盘起始位置的某⼀卷的起始位置和结束位置存储在了操作⽅法内部的局部变量⾥,它在get_Name和set_Name⾥是两个常量(因为卷头⾥没有该块空间的位置和描述信息⾃然就⽆法反射),所以传⼊this对象后获得this的其实位置,然后分别加上this的起始位置就得到了那块匿名空间的起始位置和结束位置,然后进⾏操作;A再举个例⼦,⼀栋⼤楼(对象)⾥有5层,第⼀层作为元数据存储区(卷头)不参与存储对象字段,然后我知道要找的字段名如name(对应某⼀层作为⼀块空间)【字段名存储在set_Name⽅法⾥的局部变量⾥】,只需要告诉我this指针(⼤楼起始地址),然后我就跑到⼀楼查看name的元数据信息包括起⽌地址类型等,从⽽知道我要找的name字段在3楼,所以我再跑三楼地板到天花板这部分获取数据或存储数据;这种⽅式就是⾮⾃动属性的实现⽅式,显然第⼀楼⾥需要花⼀些空间来存储name的⼀些描述信息;B⽽现在我不知道我要找的是什么(但是类型是知道的,毕竟get_Name⽅法的返回值类型就是我需要的类型,我去找其实就是set_Name,⽽要找的数据信息就是set_Name⾥⾯的局部变量),我只是知道我要找的空间是第三楼的地板到天花板这部分(这个就是偏移量/起⽌地址,相对⼤楼⼀层,然后这个偏移量也是记录在set_Name和get_Name⾥;⽤完就释放,当然有份默认的⽤于初始化每次调⽤),所以我跑到⼤楼后(this指针告诉我⼤楼在哪)直接跑到三楼对三楼进⾏操作;所以⾃动属性也算是⼀种优化;注意,上⾯图⾥的代码的Price是对显式字段price的引⽤,⽽且反射是可以获得的,因此编译器这时候就不会创建⼀个没有元数据的空间来⽤于set_Price get_Price的操作了,⽽是set_Price⾥存储的偏移数据也是指向price这个有元数据的字段上;然后之所以还是需要有这个显式字段的反射信息是因为这样的显式定义使得price不仅仅可以被set_Price操作,还能被类⾥的其他⽅法操作;。
java 字段 的定义
java 字段的定义Java字段的定义。
在Java编程语言中,字段(Field)是指类或接口中声明的变量。
字段可以用来存储对象的状态信息,它们定义了对象的属性和特征。
在Java中,字段可以包括基本数据类型(如int、double、boolean等)或者引用类型(如String、自定义类等)。
字段的定义通常包括访问修饰符、数据类型和字段名。
访问修饰符可以是public、protected、private或者默认访问修饰符。
数据类型指定了字段可以存储的数据类型,字段名则是用来标识字段的名称。
例如,下面是一个简单的Java字段的定义:java.public class Person {。
private String name; // 字段名为name,类型为String,访问修饰符为private.public int age; // 字段名为age,类型为int,访问修饰符为public.protected boolean isStudent; // 字段名为isStudent,类型为boolean,访问修饰符为protected.}。
在上面的例子中,我们定义了一个Person类,包含了三个字段,name、age和isStudent。
这些字段分别用private、public和protected修饰符进行修饰,指定了它们的访问权限。
字段的定义可以帮助我们组织和管理数据,使得代码更加清晰和易于维护。
通过定义字段,我们可以在类或接口中存储和访问对象的状态信息,从而实现更加灵活和强大的程序逻辑。
总之,Java字段的定义是Java编程中非常重要的一部分,它为我们提供了一种有效的方式来管理对象的状态信息,从而实现更加健壮和可靠的程序设计。
字段(Field)与属性(Property)
C#: 字段(Field)与属性(Property)基本概念字段与属性的关系属性访问器的使用附:实例(本文中的代码均在VS2005中运行过。
启动VS2005,新建一个C#语言的控制台应用程序项目,将本文中代码复盖原自动生成的代码,启动调试,就可以看到运行结果)一)基本概念看下面一段代码:……User zs =new User(); = "张三";Console.WriteLine("姓名: " + );……可能有人推断,Name一定是User类的一个成员变量。
----对于C#而言,这个推断十有八九是错的。
C#的类成员在C++基础上有了扩展,“字段”与“属性”就是扩展后的两种类成员。
C#类中的“字段”,与C++类中的“变量”及JAVA中的“域”是同一概念。
对私有字段的读写,只能通过类内的方法。
C#专门提供了一个对私有字段进行读写的特殊“方法”。
这种"方法"不需要参数,但有含get{}或set{}的代码块。
这种特殊的“方法”,在C#中称为“属性”。
例如:public class User{private string m_name; //m_name为字段public string Name //Name为属性,它含有代码块{get{return m_name;//读取(返回m_name值)}set{m_name = value;//为m_name赋值}}User类中的m_name为“字段”,而Name则为“属性”,属性代码块中get 与set,称为属性访问器。
私有的字段m_name可以通过公开的属性Name对它进行读写操作。
通过“属性”读取“字段”值时,将触发get访问器;通过“属性”为“字段”赋值,将触发set访问器。
如:User zs =new User(); = "张三";//此句将自动触发set访问器,将"张三"赋予m_nameConsole.WriteLine("zs的姓名是: " + );//此句将自动触发get 访问器,显示m_name的值。
在属性与字段中,为什么要给字段设private
在属性与字段中,为什么要给字段设private字段(field)通常定义为private,表⽰类的状态信息。
CLR⽀持只读和读写字段。
值得注意的是,⼤部分情况下字段都是可读可写的,只读字段只能在构造函数中被赋值,其他⽅法不能改变只读字段。
常见的字段定义为:public class Client{private string name; //⽤户姓名private int age; //⽤户年龄private string password; //⽤户密码}如果以public表⽰类的状态信息,则我们就可以以类实例访问和改变这些字段内容,例如:public static void Main(){Client xiaoWang = new Client(); = "Xiao Wang";xiaoWang.age = 27;xiaoWang.password = "123456"}这样看起来并没有带来什么问题,Client实例通过操作公有字段很容易达到存取状态信息的⽬的,然⽽封装原则告诉我们:类的字段信息最好以私有⽅式提供给类的外部,⽽不是以公有⽅式来实现,否则不适当的操作将造成不必要的错误⽅式,破坏对象的状态信息,数据安全性和可靠性⽆法保证。
例如: xiaoWang.age = 1000; xiaoWang.password = "";显然,⼩王的年龄不可能是1000岁,他是⼈不是怪物;⼩王的密码也不可能是“@&;”这些特殊符号,因为ATM机上根本没有这样的按键,⽽且密码必须是6位。
所以对字段公有化的操作,会引起对数据安全性与可靠性的破坏,封装的第⼀个原则就是:将字段定义为private。
那么,如上⽂所⾔,将字段设置为private后,对对象状态信息的控制⼜该如何实现呢?⼩王的状态信息必须以另外的⽅式提供给类外部访问或者改变。
同时我们也期望除了实现对数据的访问,最好能加⼊⼀定的操作,达到数据控制的⽬的。
C#中的域(field)和属性(property)
C#中的域(field)和属性(property)访问一个类的成员变量可以有两种方式:域、属性。
域作为public类型的成员变量访问,而属性不能直接进行访问,必须通过访问器(accessors)进行。
域(field)域(field)-域表示与对象或类相关联的变量。
-域的声明中如果加上了readonly修饰符,表明该域为只读域。
对于只读域我们只能在域的定义中和它所属类的构造函数中进行修改。
在其他情况下,域是“只读”的。
-static readonly的作用和#define、const的作用类似。
区别是:const型表达式的值是在编译时形成的,而static readonly表达式的值直到程序运行时才形成。
如:public class a{public static readonly int x = 1;}-c/c++中未经初始化的变量是不能使用的。
在c#中,系统将为每个未经初始化的变量提供一个默认值。
对于所有引用类型的变量,默认值是null。
所有值类型的变量的默认值是固定的。
对于静态域,类在装载时对其进行初始化;对于非静态域,在类的实例创建时进行初始化。
在默认的初始化之前,域的值是不可预测的。
例如下面的代码是合法的:class test{static int a = b+ 1;static int b = a+ 1;}实际上等价于:a = 1; b = 2;而下面的代码则是非法的:class a{int x = 1;int y = x + 1;}因为非静态变量x在类a实例化以前并没有初始化,代码y = x + 1无法得到正确的x的值。
属性(property)-充分体现了对象的封装性:不直接操作类的数据内容,而是通过访问器进行访问,即借助于get和set对属性的值进行读写;另一方面还可以对数据的访问属性进行控制(当然也可以通过对普通域加readonly关键字来实现。
-设计原则:属性封装了对域的操作。
关于属性与字段的区别
属性为类提供了一种很有用的封装数据的方法。
属性的使用简化了语法,如以下两个语句:o.set(o.get()+1); o.value++; 属性的灵活性:使内部数据和外界获取相分离,内部数据的更改不会影响到外界的取得。
GET访问器获取当前的属性值SET访问器设置当前的属性值,一般不期望有副作用,如设置一个属性值会同时修改另一个值,有些时候副作用也是非常有用的,如购物车中当用户添加一个新的商品放到购物框中的时候,会自动地修改商品总值。
属性和字段的比较:属性是逻辑的字段值,所谓逻辑就是属性可以返回基于字段的计算值,而字段只能直接返回它本身的值,如person类,它有一个born字段,代表出生日期,还有一个Age属性,该属性可以通过(DateTime.Now- born)计算返回年龄。
属性还可以对外实现数据的验证。
属性和字段的相似性:1.用一个非void类型声明一个名称, as shown: class Example { int field;//声明一个字段int Property { ... }//声明一个属性}2.可以用任意的访问修饰符, as shown: class Example { privat e int field; public int Property { ... } }3.都可以为静态的, as shown: class Example { static private int field; static public int Property { ... } }4.可以隐藏基类的同名称的成员, as shown: class Base { public int field; public int Property { ... } } class Example: Base { new public int field; new public int Property { ... } }5.读和写的语法都一样, as shown: Example o = new Example( ); o.field = 42; o.Property = 42; 属性和字段的不同:属性并没有保存物理数据,不直接存储数据,所以不能把属性当作参数传递给方法。
属性与字段的区别
属性与字段的区别
从两者的声明上来看,公共字段只是类⽤public修饰符所公开的简单公共变量,⽽属性则是对字段的封装,它使⽤get和set访问器来控制如何设置或返回字段值。
由于属性的实质是⽅法(get或set⽅法),在IL中是没有属性的概念的。
所以对于开发过程中常⽤的赋值和取值操作来说,使⽤公共变量肯定会⽐使⽤属性速度要快,性能上也稍⾼(⽅法和变量哪个速度不⽤说了吧)。
公共字段虽然在速度上快,但它必须开放字段为public,这样⼀来对象的调⽤者便可以直接修改其值,值的内容是否合法,运⾏中是否会出错,就没有了保障,进⽽会⼤⼤降低类的可重⽤性;相反,属性类似于⽅法,它可以对存⼊的变量的值进⾏处理,如果觉得该值不合法,可以就地变换或者直接提出警告。
这对该类的对象的使⽤安全有很⼤好处,在运⾏过程中,因公共变量值的错误⽽产⽣的问题会⼤⼤减少。
从上述内容来看,两者各有优缺点,在实际项⽬开发过程中,我们究竟选择使⽤哪⼀种⽅式呢?
如果满⾜下⾯⼏个条件,那么我们便可以⼤胆地使⽤公共字段:
1.允许⾃由读写;
2.取值范围只受数据类型约束⽽⽆其他任何特定限制;
3.值的变动不需要引发类中其它任何成员的相应变化;
属性的使⽤条件则恰好跟变量相反,只要满⾜下⾯任何⼀个条件,就应该使⽤属性:
1.要求字段只能读或者只能写;
2.需要限制字段的取值范围;
3.在改变⼀个字段的值的时候希望改变对象的其它⼀些状态;
总结:虽然在实际项⽬的开发过程中,公共字段和属性在合适的条件下都可以使⽤,但是我们应该尽可能的使⽤属性(property),⽽不是数据成员(field);把所有的字段都设置为私有字段,如果要暴露它们,则把它们封装成属性,这也是微软推荐的⽅式。
C++中的属性
C++中的属性C++中的属性⾸先我们来看⼀下C#中的属性c#中的字段通常是 private,内部使⽤。
属性是 public 或 protected,对外公开,属性通过 get set 访问器对字段提供安全、有效范围等保护。
讲概念可能不好讲,下⾯来看⼀个例⼦吧!(最简单的)class Program{private int field1; //这个field1就是字段public int Field1 //这个Fileds1就是属性{get{return field1;}set{field1=value;}}}//因为字段的访问修饰符为private外部不能访问它,但可以定义属性为public来访问。
/xieqidong/article/details/3265199C#中有属性(Property),⽽C++中却没有,其实属性对于C++⽽⾔也是⾮常重要的,请往下看。
什么是属性属性就像那些可以存储数据的变量,但在从它们中读写数据时会引发事件,换句话来说,属性就是⼀个有互作⽤的变量,⾃我更新,并在读写其⾃⾝时产⽣不同的值。
使⽤像C#这样包含属性的语⾔⾮常容易编写⼀个类,但对C++来说似乎就不太可能了,因为C++的编译器不⽀持C#那种形式的属性。
正因为此,本⽂就是要介绍如何编写带有像C#中属性的C++类。
为什么属性很重要如果你需要编写⼀个代表⼈物的对象,这个对象可能包含以下数据:全名、年龄、出⽣年⽉、性别。
如果⽤C++来编写,代码如下:class Person {public:Person( ){}virtual ~Person( ){}private: //数据成员char m_fName[20];char m_lName[20];UINT m_YearOfBirth;bool m_bGender;};注意:在⼤多数情况中,不能为了可直接使⽤,就定义⼀个数据成员为public,因为数据成员应由对象内实现的业务逻辑来维护。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
C#: 字段(Field)与属性(Property)
基本概念
字段与属性的关系
属性访问器的使用
附:实例
(本文中的代码均在VS2005中运行过。
启动VS2005,新建一个C#语言的控制台应用
程序项目,将本文中代码复盖原自动生成的代码,启动调试,就可以看到运行结果)一)基本概念
看下面一段代码:
……
User zs =new User();
= "张三";
Console.WriteLine("姓名: " + );
……
可能有人推断,Name一定是User类的一个成员变量。
----对于C#而言,这个推断十有八九是错的。
C#的类成员在C++基础上有了扩展,“字段”与“属性”就是扩展后的两种类成员。
C#类中的“字段”,与C++类中的“变量”及JAVA中的“域”是同一概念。
对私有字段的读写,只能通过类内的方法。
C#专门提供了一个对私有字段进行读写的特殊“方法”。
这种"方法"不需要参数,但有含get{}或set{}的代码块。
这种特殊的“方法”,在C#中称为“属性”。
例如:
public class User
{
private string m_name; //m_name为字段
public string Name //Name为属性,它含有代码块
{
get
{
return m_name;//读取(返回m_name值)
}
set
{
m_name = value;//为m_name赋值
}
}
User类中的m_name为“字段”,而Name则为“属性”,属性代码块中get 与set,称为属性访问器。
私有的字段m_name可以通过公开的属性Name对它进行读写操作。
通过“属性”读取“字段”值时,将触发get访问器;通过“属性”为“字段”赋值,将触发set访问器。
如:
User zs =new User();
= "张三";//此句将自动触发set访问器,将"张三"赋予m_name
Console.WriteLine("zs的姓名是: " + );//此句将自动触发get 访问器,显示m_name的值。
注意这里的, 会使有些人误以为zs有一个存储着zs姓名的成员变量Name,但实际上存放zs的姓名的成员变量是m_name(在C#称之为“字段”),只是它已被彻底隐藏起来了。
二)字段与属性的关系
一个“属性”总是与某个“字段”相关联,两者有扯不断的关系。
这种关系可分2种:
1)通过属性访问器读(或写)的值就是字段的值
如上例,属性Name的访问器读写的值就是字段m_name的值。
2)通过属性访问器读(或写)的值是对字段进行某种运算后得出的值。
两者可能是同一类型,也可能不是。
如下例int类型的Age属性的值,就是对D ateTime 类型的字段m_birthday进行计算后得出的:
……
private DateTime m_birthday;
public int Age
{
get
{
return DateTime.Now.Year - m_birthday.Year;
}
}
……
三)访问器
在属性中的只实现get访问器的,称只读属性;只实现set访问器的,称只写属性;两者都实现的,称读写属性。
(参见后面的示例)。
通过访问器,我们可以根据访问者的身份对其操作权限进行限定,并对数据的合法性进行检查。
四)附例
using System;
namespace Field_Property
{
class User
{
private string m_name;
private DateTime m_birthday;
public User(string name)
{
this.m_name = name;
}
public string Name //读写属性
{
get { return m_name; }
set {m_name = value ; }
}
public DateTime Birthday //只写属性
{
set
{
if(value< Convert.ToDateTime("1900-1-1") || value.Year > DateTime.Now.Year - 3) Console.WriteLine("年龄有误!");
else
m_birthday = value;
}
}
public int Age //只读属性
{
get
{
return DateTime.Now.Year - m_birthday.Year;
}
}
}
class Program
{
static void Main()
{
User zs = new User("张三");
zs.Birthday = Convert.ToDateTime("1980-1-1");
Console.WriteLine("姓名: "+ );
Console.WriteLine("年龄: "+ zs.Age);
Console.ReadKey();
}
}
}
注:DateTime是结构。
在VS2005代码编辑界面右击“DateTime”,在弹出的菜单中选“转到定义”,可以看到它的定义。