• 【Java】- 面向对象三大特征


    一、面向对象和面向过程的区别

      1、面向过程(Procedure Oriented 简称PO

        看名字它是注重过程的。当解决一个问题的时候,面向过程会把事情拆分成: 一个个函数和 数据(用于方法的参数) 。然后按照一定的顺序,执行完这些方法(每个方法看作一个个过程),等方法执行完了,事情就搞定了。
        举例: 大象装冰箱
          1、打开冰箱门
          2、将大象放进冰箱
          3、关闭冰箱门

      2、面向对象(Object Oriented简称OO

        看名字它是注重对象的。当解决一个问题的时候,面向对象会把事物抽象成对象的概念,就是说这个问题里面有哪些对象,然后给对象赋一些属性和方法,然后让每个对象去执行自己的方法,问题得到解决。
          举例: 大象装冰箱
            1、对象:冰箱
               方法:打开门(),关闭门()
            2、对象:大象
               方法:进入()
            3、demo(主方法)
            4、执行:.冰箱.打开(),大象.进入(),冰箱.关闭(冰箱)

    二、面向对象三大特征

      1、封装

        a、定义

          将代码通过权限修饰符来限定甚至隐藏起来,起到部分代码不可见从而减少被外部类对象调用修改的风险。
          权限修饰范围如下:
          
          从表格中可以看出从上到下封装性越来越差 

        b、this关键字

          this关键字代表当前对象,采取this.属性,this.方法可以来进行操作当前的属性和方法

        c、内部类(Inner Class

          定义在一个类(A)中的一个类(B),可以对代码进行有效的封装,且相对于内部类(B)来说A就是外部类,内部类B可以 调用外部类中的一切属性和一切方法,不包括匿名方法,和代码块

      2、继承

        a、定义

          类与类之间达成 "is a" 的关系,比如:A继承B,那么A就是父类(基类),B就是子类(派生类)
          注:1、java中类的继承是单继承的,即一个类的父类只能有一个
            2、java中类的继承可以传递,C继承B,B继承A,那么C可以间接的继承了A,C中拥有A中的属性和方法(不包括 私有)

        b、继承的好处

          子类可以拥有父类除了private修饰的所有的属性和方法,从而实现了代码的复用

        c、继承类加载执行顺序

          B继承A
            0)、加载A的类模板
            1)、A产生静态区,加载A的静态方法,静态属性和静态代码块即:static 修饰的属性,static修饰的方法,static修饰的代码块
            2)、加载B的类模板
            3)、B产生静态区,加载B的静态方法,静态属性和静态代码块即:static 修饰的属性,static修饰的方法,static修饰的代码块
            4)、堆内存开辟空间,加载父类A的非静态元素(属性,方法,代码块,构造方法)
            5)、执行父类A代码块/执行父类A构造函数
            6)、堆内存开辟空间,加载子类B的非静态元素(属性,方法,代码块,构造方法)
            7)、执行子类B代码块/执行子类B构造函数
            8)、将堆内存的地址引用传递给占内存开辟的变量

        d、final修饰符

          修饰类:即为最终的类,不可被继承
          修饰方法:即为最终的方法,不可被重写
          修饰属性:即为最终的属性
            当属性为基本类型,则在声明时必须赋值,且属性不可修改。
            当属性为引用类型,则声明时可以不复制,但仅保留一次赋值机会,且赋值后,属性的值(地址)不可被修改

        e、super关键字

          在子类对象内部使用,可以代替父类对象
          super.属性-->调用父类的属性
          super.方法-->调用父类的方法
        备注:
          子类在调用构造函数时,会默认调用super.父类构造函数(隐式构造函数)。
          若是子类调用构造函数时,自己写super.父类构造函数,那么super.父类构造函数必须写在子类构造函数中的第一行
          如果子类构造方法中既没有显式调用父类的构造方法,而父类没有无参的构造方法,则编译出错。

      3、多态

        a、定义

          父类引用指向子类的对象,此时形成多态的效果

        b、举例说明

          定义一个animal类如下:
     1 public class Animal {
     2 
     3     /**
     4      * 定义一个animal父类
     5      * 添加一个属性为name
     6      * 添加一个方法为eat()
     7      */
     8 
     9     public String name;
    10 
    11     public void eat(){
    12         System.out.println("动物正在进食");
    13     }
    14 
    15 }

         定义一个dog类,且dog类继承animal

    1 public class Dog extends Animal {
    2     
    3     /**
    4      * 定义一个dog类来继承animal
    5      */
    6      
    7 }

         此时我们在主方法中进行new 一个dog对象来看下

     1 public class TestMain {
     2 
     3     /**
     4      * 定义一个测试类
     5      * 类中定义一个主方法
     6      * @param args
     7      */
     8 
     9     public static void main(String[] args) {
    10 
    11         Dog dog = new Dog();
    12         dog.eat();
    13 
    14     }
    15     
    16 }

        执行结果为:

        
        由此可知子类继承父类,也就继承了父类的所有的非private修饰的方法和属性,我们在dog类中重写父类的eat()方法
        
     1 public class Dog extends Animal {
     2 
     3     /**
     4      * 定义一个dog类来继承animal
     5      */
     6 
     7     public void eat(){
     8         System.out.println("狗狗正在进食");
     9     }
    10 }

         此时我们在主方法中再次运行一下,结果如下:

         
         由此我们可以知道当子类继承父类时,子类若是重写了父类的eat()方法,运行的结果是执行子类的方法,若是子类没有重写方法,那么就会直接调用父类的eat()方法
         以下为多态的演示:
         我们在dog类中在定义一个方法,且new Dog对象时,我们用父类来接收,代码如下:
     1 public class Dog extends Animal {
     2 
     3     /**
     4      * 定义一个dog类来继承animal
     5      */
     6 
     7     public void eat(){
     8         System.out.println("狗狗正在进食");
     9     }
    10 
    11     //新写一个dog类独有的方法
    12     public void run(){
    13         System.out.println("狗狗正在奔跑");
    14     }
    15 }

        此时我们在用父类来接受子类的对象

        

        你会发现,我们找寻不到Dog类中独有的run()方法,接着我们在执行一下eat()方法
        
        输出的是Dog类中重写的eat()方法,是不是很神奇,那么此时我们在纵向思考下,假设我们现在有一个Cat类也继承Animal类并且重写了eat()方法,那么我们若是在定义一个Cat类继承Animal并且重写eat()方法
    1 Animal animal = new Cat();
    2 animal.eat();
        此时执行出的结果就会是 “猫咪正在进食”,我都是用Animal类型接受的,但是我new的对象不同,我就会输出不同的结果,这就是多态;
        那我们要执行dog的独有run()方法怎么办呢?此时就要进行向下转型
        
        进行向下转型后就会出现Dog独有的run()方法,由此我们总结以下堕胎的特性:
          1、必需存在继承关系
          2、子类必需重写了父类的方法
          3、父类来收子类的对象 Animal animal = new Dog() 此处就是向上转型。我new出一个狗的对象,用Animal动物来接受,相当于我说狗是一种动物,这是完全合理的。 总结为接受的类的类型必需大于或者等于子类
          4、父类接受子类对象后,调用的方法或者属性都是父类中拥有的方法或者属性,但是执行的结果若是子类有重写,那就执行执行子类重写的方法,若是子类没有重写方法,那么执行父类自己的方法
          5、父类接受子类对象后,若是调用子类独有的方法或者属性,必需要将父类类型向下转型为子类类型
     
    以上就是面向对象的三大特性,到此结束!!!
     
     
     
     
     
     
     
     
     
     
     
     
     
     
     

  • 相关阅读:
    ajax 通过回调函数获取异步数据
    (淘宝无限适配)手机端rem布局详解(转载非原创)
    rem在响应式布局中的应用
    移动端页面适配解决方案
    flex 布局,flex-grow 宽度未等比放大问题解决办法
    flex 布局
    bootstrap Modal 模态框垂直居中
    require.js实现单页web应用(SPA)
    解决 html5 input type='number' 类型可以输入e
    jquery 的ready() 与window.onload()的区别
  • 原文地址:https://www.cnblogs.com/tar8087/p/14391501.html
Copyright © 2020-2023  润新知