常量是表示常量值(可在编译时计算的值)的类成员。
常量隶属于类型(类和结构体)而不属于对象,因此没有“实例常量”一说。可用只读实例字段来充当“实例常量”。
需要注意的是,只读字段是变量而非常量。
// 声明:
[访问修饰符] const 类型 <常量名> = 常量值;
// 例如:
public const int A = 100;
private const string S_ID = "SSS-SSA";
字段是一种表示与对象或类型(类和结构体)关联的变量。
// 字段的声明:
[字段访问修饰符] 类型 <字段名> [ = 初始值];
字段访问修饰符(一个或多个组合):
new
public
protected
internal
private
static
readonly
volatile
// 例如:
struct Man
{
private int age;
public static readonly string name = "JJ";
}
class Book
{
int id;
string name;
}
class Man
{
// 实例字段
public string name;
}
...
// 使用
Demo1 demo1 = new Demo1();
demo1.a = "YY";
class Man
{
public static string name;
}
...
// 使用
Demo2.a = "UU";
字段初始化时机,实例字段初始化在实例创建时;静态字段初始化于类或结构体被加载时。静态字段只被初始化一次;实例字段每当实例被创建时被初始化一次。
属性语法是字段的自然延伸。 字段定义数据的存储位置;而属性包含了get和set访问器,通过这两个访问器可以用于检索该属性的值或者对其赋值。
// 属性的声明:
// 1.简略的声明:
[属性访问修饰符] 类型 <属性名> {属性访问器声明}
// 2.完整的声明:
[字段访问修饰符] 类型 <字段名> [= 初始化值];
[属性访问修饰符] 类型 <属性名> {属性访问器声明}
属性访问修饰符最常用:
public
public static
字段访问修饰符:
因为要保护起来所以一般是private 和 private static
属性访问器声明:
get 和 set 之一或全部
// 例如:
class Student
{
// 简略声明
public int age { get; set; }
// 完整声明
private static string name;
public static string Name
{
get { return name; }
set { name = value; }
}
}
class Man
{
// 字段
private int age;
// 属性
public int Age
{
get
{
return this.age;
}
set
{
if (value >= 0 && value <= 150)
this.age = value;
else
throw new Exception("年龄错误!人类年龄应该介于0到150岁之间");
}
}
}
不管是简略声明还是完整声明,生成属性声明后光标会定位数据类型上,默认类型是int,如果需要更改就直接输入新的类型。
类型修改完毕后(或者打算使用默认的数据类型)接着按一次Tab键光标会跳到属性名部分,直接修改属性名即可。
一般来说,属性是对字段的保护,比如: man.age = 1000 (某人的年龄为1000岁) , 在正常情况下一个人是不能活到1000岁的,但使用字段时却可以这样赋值,尽管是错误的。
其他编程语言如 Java 和 C++ 使用get和set方法来保护字段:
// Java代码
public class Man {
// 年龄字段
private int age;
// get方法
public int getAge() {
return this.age;
}
// set方法
public void setAge(int age) {
if (age >= 0 && age <= 150)
this.age = age;
else
throw new Exception("年龄错误!人类年龄应该介于0到150岁之间");
}
}
class Man
{
// 存储数据的字段
private string name;
// 保护字段的属性
public string Name
{
get { return name; }
set { name = value; }
}
}
Man man = new Man();
// value是一个上下文关键字,在set访问器这个
// 作用域内表示外部传进来的值,如:
man.Name = "KK";
// 此时value就是"KK".
属性其实是一种语法糖,内部的实现其实是生成了两个方法(get_属性名()和set_属性名(属性类型))。当我们使用属性的get访问器时它会去调用get_属性名()方法,当我们使用属性的set访问器时它回去调用set_属性名()方法。
索引器使得对象能够用与数组相同的方式进行索引。顾名思义,索引器是用来检索集合的。
索引器一般用在集合类。
class IndexerDemo
{
private Dictionary<string, int> dic = new Dictionary<string, int>();
public int? this[string name]
{
get
{
if (this.dic.ContainsKey(name))
return this.dic[name];
else
return null;
}
set
{
if (this.dic.ContainsKey(name))
this.dic[name] = value.Value;
else
this.dic.Add(name, value.Value);
}
}
}
class Demo
{
static void Main(string[] args)
{
IndexerDemo i = new IndexerDemo();
i["JJ"] = 20; // 赋值
var man = i["JJ"]; // 通过下标的方式索引到数据
}
}