• 15-01-10 C# 面向对象 09


    面向过程;面向的是完成这件事儿的过程,强调的是完成这件事儿的动作;

    用面向过程的思想去解决问题,当执行这件事的人不同的时候,我们必须为他量身定做不同的方式来解决问题;

    面向对象;找个对象帮你做事; 面向对象就是屏蔽差异,写出通用的代码; 对象一般都是被动的那个;

    我们在代码中描述一个对象,通过描述这个对象的属性和方法;

    我们把这些具有相同属性和相同方法的对象进行进一步的封装,抽象出来类这个概念;

    类就是个模子,确定了对象应该具有的属性和方法;对象是根据类创建出来的;

    [public] class 类名

    {  

    字段;

    属性;

    方法;

    }

    如果方法前面加了static,那么调用的时候就要用类名.方法 ;如果这个方法和Main函数在同一个类中,那么可以省略类名,直接写方法名;

    写好了一个类之后,我们需要创建这个类的对象,我们管创建这个类对象过程称之为类的实例化;使用关键字new; Person p = new Person(); 跟结构一样,通过对象.字段的方式调用;p.age = 24;

    public void CHLSS()

    {

     Console.WriteLine("我叫{0},我今年{1}岁了",this._name,this._age);

    }

    this表示当前类的对象; 通过对象.方法名的方式调用;p.CHLSS();

    类是不占内存的;而对象是占内存的;

    Person p; 跟int a;其实都是一个道理,声明一个变量;

    我们自己写的类,我们称之为自定义类;

    Person p;如果不创建对象,它的值是null;null在内存中是不占内存的; 如果创建了对象,那对象的字段就有了初值,因此开辟了内存空间;与其说对象占内存,不如说类当中的字段占内存;

    如果方法不是static的,叫做非静态方法;那么调用它的时候,应该先创建一个对象,在用对象.的方式去调用方法;

    结构和类的区别,结构是面向过程的,类是面向对象的;结构不具备面向对象的任何特征;类是真正的面向对象的;

    属性的作用就是保护字段;对字段的赋值和取值进行限定;

    属性应该写在类当中

    public string _name;

    public string Name

    {

     get {return _name;}

     set {_name = value;}

    }

    属性的本质是两个方法,一个是get(),控制取值,一个是set();控制赋值;

    通过反编译器可以看到程序的源代码;先把写好的程序编译一下,编译成功后,在文件资源管理器中找到bin下的debug目录下的.exe可执行文件,把它拖到反编译器 里面;就可以看到源代码;如果找到了属性,但是还想继续看下面的代码,先在上面把C#转换为IL&Bytes,继续往里点到最后,再把IL中间语言转化为C#,就能看懂代码了;

    fields字段;methods方法;Properties属性

    给字段赋值的时候会执行set方法,外面传进来一个值,通过属性,把值传给字段; 赋值的时候不能给字段赋值,要通过属性赋值,虽然是给属性赋值,但是最终赋值到的还是字段;属性在中间只起到过渡中间的作用;

    当你给属性赋值的时候,首先会执行set()方法; 当你输出属性的值的时候,会执行get()方法

    蓝色的长方体是字段;扳手图标是属性;

    通过属性有2种方式对字段的取值和赋值进行限定;一个是在set()方法里面,一个是在get()方法里面;

    在整个过程中,属性是没有存储值的。

    打属性的快捷键 Ctrl+R,E两下回车;

    字段是女人,存储数据用的,我们要好好保护起来;不能轻易得被别人访问到;属性才是男人,所有跟外界打交道的事应该交给属性去做;因此字段的访问修饰符是 private

    访问修饰符 public:公开的,公共的,在哪都能访问  private:私有的,只能在当前类的内部进行访问,出了这个类就访问不到了;

    类中,如果字段不加访问修饰符,默认就是private;

     get

    {    

    if(_gender != '男' && _gender != '女')  

       {

        return _gender = '男'; 

       }

          return _gender;

     }

    set

      if(value < 0 || value > 100)

      { 

        value = 0;

      }    

      _age = value;

      }

    对同一个属性,在get()中控制值和在set()中控制值的效果是一样的; 等我们学了构造函数,在构造函数中也可以设定;

    并不是所有的属性都有get()和set(); 如果一个属性既有get()又有set()我们称之为可读可写属性;只有get()我们称之为只读属性 只有set()我们称之为只写;

    在set里面我们控制的是value的值,在get里面我们控制的是字段的值,先set()后get()因为先赋值后取值;

    字段在类中必须是私有的,属性是公有的; 类中的成员,不加访问修饰符,默认是private;

    给对象的每个属性赋值的过程叫做对相的初始化;

    看一个成员是不是静态成员,就要看这个成员有没有被static修饰;

    在非静态类中,即可以有实例成员,也可以有静态成员; 在调用实例成员的时候,需要使用对象名.实例成员(); 在调用静态成员的时候,需要使用类名.静态成员名; 静态成员必须使用类名去调用,而实例成员使用对象名调用;

    在非静态类中可以有静态属性,静态字段,非静态属性,非静态字段,静态方法,非静态方法;

    静态函数中,只能访问静态成员;不允许访问实例成员; 实例函数中,既可以使用静态成员,也可以使用实例成员; 静态类当中只允许有静态成员;不允许出现实例成员;

    静态类不能创建实例对象,因为在调用静态成员的时候是用类名.的方法去调用,因此即使能够创建静态类的对象,也是没有意义的;

    什么时候使用静态类:如果你想要你的类当做一个"工具类"去使用,这个时候可以考虑将类写成静态类; 我们把经常会使用的函数封装到一个类当中,我们称这个类是工具类;

    静态类的特点:1.调用方便; 2.静态类在整个项目中,资源共享。

    类是不占内存的,但是对象是占内存的,不过静态类例外;静态类没有对象,静态类的成员由于没有对象,因此只能用静态类本身来存;所以静态类本身是占内存的;

    堆   栈    静态存储区域(存的是静态类的资源) 在整个项目中,谁都可以访问静态存储区域,因此也就造成了静态类在整个项目中资源共享;

    QQ登陆之后,把账号,密码保存到一个静态类当中;因此访问不同的模块的时候不需要重新输入用户名和密码;

    .net释放资源是用GC来完成的,垃圾回收器,但是有些东西是它释放不了的,比如我们所说的文件流; 静态类资源越少越好,1多的话占内存;2.只有在程序全部结束之后,静态类才会释放资源;所以静态类不要太多,它会始终消耗你的资源;

    构造函数用来创建对象,并且可以在构造函数中对对象进行初始化(给对象的每个属性依次的赋值);

    构造函数是用来创建对象的特殊方法; 1.构造函数没有返回值,连void都不能写 2.构造函数的名称必须跟类名一样;

    构造函数可以有参数,new对象的时候传递函数参数即可

    如果不指定构造函数,则类有一个默认的无参构造函数。如果指定了构造函数,则不再有默认的无参构造函数,如果需要无参构造函数,则需要自己来写

    类里面可以有字段,属性,方法,构造函数;

    构造函数的访问修饰符必须是public;

    public Student()

    {  

    }

    在我们创建对象的时候,首先会执行构造函数; 如果想初始化对象的话,就在构造函数中对对象的每个属性赋值;

    public Student

    (string name,int age,char gender,int chinese,int math,ing english)

    {  

    this.Name = name;  

    this.Age = age;  

    this.Chinese = chinese;  

    this.Gender = gender;  

    this.Math = math;  

    this.English = english;

    }

    创建对象的时候会调用构造函数,要求你传入6个参数,构造函数把你传入的值依次得赋值给这个对象对应的属性;

     Student zsStudent = new Student("张三",18,'男',100,100,100);    

    //zsStudent.Name = "张三";    

    //zsStudent.Age = 18;    

    //zsStudent.Gender = '男';    

    //zsStudent.Chinese = 100;    

    //zsStudent.Math = 100;    

    //zsStudent.English = 100;  用了有参数的构造函数这些给属性赋值的代码就不必用了;因此构造函数可以大大减少代码量;    

    zsStudent.SayHello();    

    zsStudent.ShowScore();

    new关键字;     Student s = new Student();    

    new帮助我们做了三件事;     1.在内存中开辟一块空间;     2.在开辟的空间中创建对象;     3.调用对象的构造函数进行初始化对象;     

    这三步有一步完不成这个对象就创建不出来;因此构造函数的访问修饰符必须是public;如果是private的话其他类里面创建对象的时候就访问不到这个构造函数了;    

    public Student(string name,int age,char gender)   

    {      

    this.Name = name;      

    this.Age = age;      

    this.Gender = gender;    

    }

    构造函数可以重载,也就是有多个参数不同的构造函数。

    我们写好一个类之后,就有一个自带的默认无参的构造函数; 类当中会有一个默认的无参的构造函数,当你写一个新的构造函数之后,不管是有参数的还是无参数的,那个默认的无参数的构造函数都被干掉了;

     public Student(string name,int chinese,int math, int english):this(name,"0",'男',chinese,math,english)   

    {         

    }

    public Student(string name,int chinese,int math, int english):this(name,"0",'男',chinese,math,english)

    调用的时候   Student zhangSan = new Student("张三",100,100,100);

    执行的过程是先调用这个构造函数,调用这个构造函数的时候又调用全参的构造函数; 把(string name,int chinese,int math, int english)这些参数传给全参的构造函数;再由全参的构造函数赋值给每个属性;归根结底调用的是全参的构造函数; 这就是通过类中的构造函数去显示的调用另外的构造函数;目的就是减少冗余代码;

    this的作用 1.代表当前类的对象;  2.在类当中显示的调用本类的构造函数:this

    类里面可以有字段,属性,方法,构造函数,析构函数;

    析构函数

    ~Student()    //这就是析构函数;

    {   

    }

    当程序结束的时候,析构函数才被执行;

    析构函数对我们的作用就是释放资源;.net有GC  GarbageCollection垃圾回收器,能够自动的帮助我们释放资源; 但一般我们不去手动的调用GC帮我们回收,而是我们的程序自动使用GC帮我们回收程序;这时候有个问题,有可能我们的程序结束后,GC没有马上帮助我们 释放资源;如果你想要资源马上去释放的话,那我们就要去使用析构函数;如果不使用析构函数的话,那么就由我们的垃圾回收器GC自动帮我们释放资源;

    public class Ticket

    {  

    private double _distance;    

    public double Distance  

      {     

      get{return _distance;

      }   

    }     

    public Ticket(double distance)   

    {      

     if(distance < 0 )      

       {        

            distance = 0;       

        }      

        this._distance = distance;      //在构造函数中也能控制字段的值的非法性,另外还有在属性的get和set方法中也能控制字段的非法性;    

    }

       privete double _price;      

       public double Price   

       {

          get

              { 

                  if(_distance > 0 && _distance <= 100)          

                   {  return distance * 1.0; }         

                 else if(_distance >= 101 && _distance < 200)          

                   {  return distance * 0.95; }           

                 else if(_distance >= 201 && _distance < 300)          

                    {   return distance * 0.9;}           

                  else           

                  {   return distance * 0.8;}        

                   }             //get是一个天然的方法;在取值的时候就会调用这个方法;

               }

         public void ShowTicket()     

        {        

         Console.WriteLine("{0}公里的价格是{1}",Distance,Price);      

        }   

    }

  • 相关阅读:
    养生之《爱的供养》
    道家养生,与佛家养德
    个人的佛法·5·活着,与死去
    自我囚禁与安住于轮回
    个人的佛法·4·我是不是东西?
    个人的佛法·2
    我们都是生命的灯塔
    大O表示法是什么?
    uni-app商城项目(01)
    2059
  • 原文地址:https://www.cnblogs.com/hhsfrank/p/4215214.html
Copyright © 2020-2023  润新知