分享一下: C# 面向对象系列笔记(一) ,希望对大家有所帮助
第一天
1.对象
对象必须特指,实实在在存在的东西;
2.类 (主要包含: 属性,方法和字段)
1>.概念:类创建了对象模子,确定了对象将要有意的属性方法
Eg: 类就像盖大楼的图纸
对象就是按图纸盖出来的大楼
程序中: 类是抽象的(如 人类)对象是具体的实例
2>创建:创建类一定要从本程序上右键进行添加类(不能再Program类中直接添加)
3>类的实例化:
类设计好了以后,我们应该去创建对象,我们管这个过程叫做类的实例化,
4>类的初始化:
我们创建好一个对象之后,给对象的每个属性依次赋值,这个过程叫做对象的初始化
5> 语法
class 类名
{
类中的成员;
}
class:表示声明类的关键字
6> 使用方法
类型 对象名 = new 类名
注意:new 以后才叫创建对象,从内存堆中开辟空间
在类中,成员前面如果不加任何访问修饰符,那么默认就是private。
命名:符合Pascal命名规范,每个单词的首字母都要大写,其余每个字母小写。
2. 字段 方法 属性
字段:字段在类中为一的作用就是存储数据
方法:方法是描述这个对象的行为
属性:保护字段,可以对字段的取值和设值进行限定
属性的本质就是两个函数 一个叫get,一个叫set;
属性保护字段的两种方式 一个get中限定,一个set中限定
比喻:属性—>男人:外部打交道
字段—>女人:在家存数据
属性分三种:1> 既有get又有set -à可读可写属性;
2> 只有get:只读属性
3> 只有set:只写属性
注意:方法中调用变量时必须加this.,否则有可能跟你定义的变量重复;
3. 引用类型和值类型:
值类型:int,double,char,bool,decimal,struct,emun;
引用类型:string ;数组; 自定义的类;
内存中的两块空间: 堆和栈
值类型:值类型的值是存在栈中的;
引用类型:引用类型的值是存储在堆中的,栈中存的是变量在堆中的内存地址;
值类型和引用类型的最重要区别:
<1> 值类型在赋值传递的是传递值的本身。
<2> 引用类型在赋值的时候传递的是地址;
4.this关键字:
1> 就代表当前类的对象
Eg:
publicvoid SayHello()
{
//string Name = "ABC";
Console.WriteLine("我叫{0},我今年{1}岁了,我是{2}生", this.Name, this.Age, this.Gender);
}
2> 调用当前自己类中的构造函数
Eg:
public Student(string name, int chinese, int math, int english)
: this(name, 0, 0, chinese, math, english)
{
}
5. 构造函数
就是为了解决在给类的在初始化时,属性非常多的对象
1>定义:构造函数就是一种特殊的函数:
原因一:构造函数的名称必须和类名一致;
原因二:构造函数不允许有返回值,并且连void都不用写;
2>注意:每个类都有一个默认的无参的构造函数,当你在类中写了一个新的构造函数之后,那么这个构造函数就被干掉了;
3>构造函数是可以重载的 ;
解决构造函数重载时的代码冗余问题:
----à使用this关键字;
Eg:
public Student(string name, int age, Gender gender)
{
//保护字段的第三种方式就是在构造函数中进行限定
if (name != "小兰")
{
name = "小兰";
}
this.Name = name;
if (age < 0 || age > 100)
{
age = 16;
}
this.Age = age;
this.Gender = gender;
}
6. 析构函数
程序结束时执行的函数,一般用于资源的释放(等同于GC)
//提供一个析构函数
~Person()
{
Console.WriteLine("我是本类当中的析构函数");
}
---------------------------------------------------------------
Person zsPerson = newPerson();//调用了构造函数
Console.ReadKey();
//GC
7.用new来创建对象new所做的三件事(new的时候已经调用了构造函数)
----à在堆中开辟空间 //内存中自动完成
----à在开辟的堆空间中创建对象; //内存中自动完成
----à调用对象的构造函数中进行初始化; //手动
8. 静态与非静态的区别
如果当前成员是静态成员,那么需要加上static关键字进行修饰。
如果当前成员不是静态成员,那么不需要static关键字修饰
1> 调用的区别:
-----à静态成员在调用的时候需要使用类名来调用;
-----à但是非静态类在调用的时候适用对象名来调用;
Eg:Person zsPerson = newPerson();
zsPerson.SayHello();
Person.SayHello2();
zsPerson.Name1 = "张三";
Person.Name2 = "李四";
---------------------------------------------------
Class Person
publicvoid SayHello()
{
Console.WriteLine("我是Person类中的非静态函数");
}
publicstaticvoid SayHello2()
{
// _name1
Console.WriteLine("我是Person类中的静态函数");
}
2>在非静态类中:
---à在静态类中即允许出现静态成员,也允许出现非静态成员
---à在非静态类中允许访问静态类,也可以访问非静态类
---à静态函数只允许访问静态成员
3>在静态类中:
只允许出现静态成员。
注意:静态成员是先对象一步进入内存中的。
什么时候用静态?
<1> 你的资源需要全局共享时
<2> 如果你写的类需要要当做工具来使用的时候 (典型工具类 Console)
反之用非静态;
!!!静态成员只有在整个程序结束的时候才能够被释放资源。
所以说,我们程序中静态成员应该是越少越好
9. 命名空间
如果我们的一个项目中需要访问到另一个项目,步骤:
--à添加引用
--à导入要引用的类所在的命名空间
--à将被导入类的修饰符改为public;
Internal修饰分成员表示只能在当前项目的内部访问,出啊了本项目就访问不到了
10.查看变量在内存中的地址;
调试时-à工具栏调试-à窗口-à即时
用法:& + 要查的变量名
Eg: Int number = 10;
number = 20;
string name = "张三";
name = "李四";
11.值传递和引用传递:
值传递就是将值赋值在栈中直接修改为新的值;
引用传递就是在堆中从新开辟一块空间,把新值的内存引用地址赋给栈中的name变量
Eg: Person person = newPerson();
person.Name = "张三";
Test(person); //输出的是张三
--------------------------------------
// 方法
staticvoid Test(Person per)
{
Person pp = newPerson();
pp.Name = "王五";
//pp = per;//引用传递
per = pp;
per.Name = "李四";
}
1插入整数和插入字符串内存中的区别
2内存中栈和堆中的变化
3上题中各个名字在内存中变化
4类中修改数据内存中的变化
5字符串中修改数据栈,堆的变化