A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

一、面向对象简述。
面向对象是一种现在最为流行的程序设计方法,谈到面向对象就不得不提及面向过程。
这是两种不同的程序设计方法,常见的c语言用的是面向过程,而java、c++用的是面向对象。
对两种思想抽象地定义,
面向过程是围绕功能进行的,为每一个功能写一个函数,需要考虑其中的每一个细节,以步骤划分;
而面向对象则像是组装,先确定一个系统是由哪些对象组成,再分别去设计这些对象,将它们像零件一样组装起来形成有完整功能的系统。
再具体举一个常用的例子:用这两种方法分别实现“把大象放进冰箱”。
面向过程:肢解大象-打开冰箱-放入大象-关闭冰箱
面向对象:大象(肢解功能、移动功能)、冰箱(打开功能、装载功能、关闭功能)。
面向对象的三大特性。
(1)封装:保护内部的操作不被破坏;
(2)继承:在原本的基础之上继续进行扩充;
(3)多态:在一个指定的范围之内进行概念的转换。
二、类与对象的基本概念
类与对象时整个面向对象中最基础的组成单元。
类:是抽象的概念集合,表示的是一个共性的产物,类之中定义的是属性和行为(方法);
对象:对象是一种个性的表示,表示一个独立的个体,每个对象拥有自己独立的属性,依靠属性来区分不同对象。
比如说:人类是一个类,每一个人是类中的一个对象,每个人都有身高,体重,性别,外貌等等的属性。
在编程设计中,我们需要定义一个类,再给对应的类定义具体对象。
三、类与对象的定义和使用
类定义范式:


  • class 类名称{



  •       属性;



  •       行为;



  • }



定义Person类:


  • class Person{



  •       String name;//名字



  •       int height;//身高



  •       int age;//年龄



  •       public void walk(){



  •              System.out.print(name+"会走路");



  •       }  //走路



  •       public void tell(){



  •              System.out.print("名字:"+name+";"年龄:"+age);



  •       }



  • }



类定义完成之后,无法直接使用。如果要使用,必须依靠对象,对象的产生格式(两种格式)如下:
(1)格式一:声明并实例化对象


  • 类名称 对象名称 = new 类名(); //格式



  • Person person = new Person();//Person实例



(2)格式二:先声明对象,再实例化对象


  • 类名称 对象名称 = null;



  • 对象名称 = new 类名(); //格式







  • Person person = null;



  • person = new Person(); //Person实例



不同于int、String、char等基本数据类型,类属于引用数据类型,而引用数据类型在使用时需要用内存空间的分配和使用,关键字new就是用来分配内存的。
实例化一个对象后,可以用关键字"."对对象进行类的操作,比如定义属性具体值,使用方法。


  • 对象名.属性名 = 具体值;



  • 对象名.方法名();







  • person.age = 18;



  • person.walk();



接下来用在eclipse实践一下这两种实例化对象的方法。
格式一:


  • package com.alex.classtest;







  • class Person {



  •     String name ;



  •     int age ;



  •     public void get() {



  •         System.out.println("姓名:" + name + ",年龄:" + age);



  •     }



  • }







  • public class TestDemo {



  •         public static void main(String args[]) {



  •             Person per = new Person() ;// 声明并实例化对象



  •             per.name = "张三" ;//操作属性内容



  •             per.age = 30 ;//操作属性内容



  •             per.get() ;//调用类中的get()方法



  •         }



  • }



运行结果:
姓名:张三,年龄:30
格式二:


  • package com.alex.classtest;







  • class Person {



  •     String name ;



  •     int age ;



  •     public void get() {



  •         System.out.println("姓名:" + name + ",年龄:" + age);



  •     }



  • }







  • public class TestDemo {



  •         public static void main(String args[]) {



  •             Person per = null;//声明对象



  •             per = new Person() ;//实例化对象



  •             per.name = "张三" ;//操作属性内容



  •             per.age = 30 ;//操作属性内容



  •             per.get() ;//调用类中的get()方法



  •         }



  • }



运行结果:
姓名:张三,年龄:30
我们可以发现,得到的结果是一样的。那么这两种方式的区别在哪呢?
说到这里就必须从内存的角度来分析。
首先,给出两种内存空间的概念:
(1)堆内存:保存对象的属性内容。堆内存需要用new关键字来分配空间;
(2)栈内存:保存的是堆内存的地址(在这里为了分析方便,可以简单理解为栈内存保存的是对象的名字)。

任何情况下,只要看见关键字new,都表示要分配新的堆内存空间,一旦堆内存空间分配了,里面就会有类中定义的属性,并且属性内容都是其对应数据类型的默认值。
上面两种对象实例化对象方式内存表示如下:

两种方式的区别在于①②,第一种声明并实例化的方式实际就是①②组合在一起,而第二种先声明然后实例化是把①和②分步骤来。
如果使用了没有实例化的对象,则会程序运行结果会报错。


  • package com.alex.classtest;







  • class Person {



  •     String name ;



  •     int age ;



  •     public void get() {



  •         System.out.println("姓名:" + name + ",年龄:" + age);



  •     }



  • }







  • public class TestDemo {



  •         public static void main(String args[]) {



  •             Person per = null;//声明对象



  •             //per = new Person() ;//实例化对象



  •             per.name = "张三" ;//操作属性内容



  •             per.age = 30 ;//操作属性内容



  •             per.get() ;//调用类中的get()方法



  •         }



  • }



运行结果:


  • Exception in thread "main" java.lang.NullPointerException



  •     at com.wz.classandobj.TestDemo.main(TestDemo.java:15)



错误信息表示的是“NullPointerException(空指向异常)”。是因为程序只声明了Person对象,但并没有实例化Person对象(只有了栈内存,并没有对应的堆内存空间),程序在编译的时候不会出现任何的错误,但是在执行的时候出现了上面的错误信息。

四、对象引用传递初步分析
引用传递定义上指的是同一块堆内存空间,可以同时被多个栈内存所指向,不同的栈可以修改同一块堆内存的内容。
也就是说同一个对象的属性内存被两个不同命名的对象共同使用。
看下面实例


  • class Person {



  •          String name ;



  •          int age ;



  •          public void tell() {



  •                    System.out.println("姓名:" + name + ",年龄:" + age) ;



  •          }



  • }



  • public class TestDemo {



  •          public static void main(String args[]) {



  •                    Person per1 = new Person() ;         // 声明并实例化对象



  •                    Person per2 = new Person() ;



  •                    per1.name = "张三" ;



  •                    per1.age = 20 ;



  •                    per2.name = "李四" ;



  •                    per2.age = 30 ;



  •                    per2 = per1 ;// 引用传递



  •                    per2.name = "王五" ;



  •                    per1.tell() ;



  •          }



  • }







输出的结果是:
姓名:王五,年龄:20
在这个过程中,内存空间是这样变化的:

垃圾:指的是在程序开发之中没有任何对象所指向的一块堆内存空间,这块空间就成为垃圾,所有的垃圾将等待GC(垃圾收集器)不定期的进行回收与空间的释放。
五、面向对象的封装性在定义类时,在class或者属性变量之前加上修饰词public、private、default、protected表示它的被访问权限。

先看属性变量没有修饰词也就是默认(default)的时候,


  • class Book{







  •     String title;



  •     double price;







  •     public void getInfo(){



  •         System.out.println("图书的名称:"+title+" 图书的价格:"+price);



  •     }



  • }







  • public class TestDemo {



  •         public static void main(String args[]) {



  •             Book book = new Book();



  •             book.title = "Quanta";



  •             book.price = 99;



  •             book.getInfo();



  •         }



  • }







输出的结果是:
图书的名称:Quanta 图书的价格:99
当属性变量修饰词为private时:


  • class Book{







  •     private String title;



  •     private double price;







  •     public void getInfo(){



  •         System.out.println("图书的名称:"+title+" 图书的价格:"+price);



  •     }



  • }







  • public class TestDemo {



  •         public static void main(String args[]) {



  •             Book book = new Book();



  •             book.title = "Quanta";



  •             book.price = 99;



  •             book.getInfo();



  •         }



  • }







运行结果:


  • Exception in thread "main" java.lang.Error: Unresolved compilation problems:



  •     The field Book.title is not visible



  •     The field Book.price is not visible







  •     at com.wz.classandobj.TestDemo.main(TestDemo.java:16)



也就是在加入private修饰词后无法再Book类的外部直接调用它的属性了。
那么如何在类外部访问Book类内的private(私有)变量呢?这时候可以用到setter、getter方法。
为Book类定义属性相应的setter和getter方法,以Book类为例:


  • class Book{







  •     private String title;



  •     private double price;







  •     public void setTitle(String title){



  •         this.title = title;



  • }



  •     public String getTitle(){



  •         return title;



  • }







  •     public void setPrice(double price){



  •         this.price = price;



  • }



  •     public double getPrice(){



  •         return price;



  • }



  •     public void getInfo(){



  •         System.out.println("图书的名称:"+title+" 图书的价格:"+price);



  •     }



  • }







  • class TestDemo {



  •         public static void main(String args[]) {



  •             Book book = new Book();



  •             book.title = "Quanta";



  •             book.price = 99;



  •             book.getInfo();



  •         }



  • }




【转载】https://blog.csdn.net/weixin_412 ... 546?utm_source=copy

1 个回复

倒序浏览
奈斯
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马