黑马程序员面试题面向对象一(封装,构造函数,this,static,单例设计模式,继承)

时间:2023-02-11 17:23:26
------- android培训java培训、期待与您交流! ----------  一面向对象概念 1 解面向对象
 (1) 面向对象是相对面向过程而言。
 (2)面向对象和面对过程都是一种思想。
 (3)面向过程强调的功能行为。
 (4)面向对象将功能封闭成对象,具备了功能的对象。
 (5)面向对象是基于面向过程的。
 (6)面向对象的三个特征:封装,继承,多态。
 
2面向对象要点
(1)相对于过程,面向对象使问题更加简单化。
(2)对象不只是指人,万物皆可为对象。
(3)面向对象使执行者变为指挥者。
(4)开发时,先找对象,再找功能,找到了直接用。
(5)没有对象时,创建对象再用。

2类与对象的关系 
(1)类:对现实生活中的事物的描述 (对象的抽象)
(2)对象:就是这类事物实实在在的个体(类的实例)
3.main函数
public static void main(String[] args)

 public :代表着该函数的访问权限是最大的。
 static :主函数是静态的,代表主函数随着类的加载就已经存在。
 void  :主函数的返回值没null 没有具体返回值。
  main:不是关键字,但是一个特殊的词,可以被jvm所识别。
 (String[] args) 函数的参数,参数类型是一个数组,该数组中的元素是字符串,JVM在调用主函数时,传入的是new String[0];

4 成员变量和局部变量
 (1)作用范围
  成员变量作用于整个类中
  局部变量作用于函数中,或者语句中。
  
  (2)在内存中的位置:
  成员变量:在堆内存中,因为对象的存在才在内存中存在。
  局部变量:在栈内存中。
  
  (3)main函数注意点:
  在类中写主函数代表该类可独立运行
  可在本类中创建本类对象,但一般不这样做。

 5 匿名对象  

 (1)匿名对象是对象的简化形式。
  (2)匿名对象调用属性没意义,调用方法有意义,因为方法里有内容。
  (3)匿名对象两种使用情况:
  <1>当对对象方法仅进行一次调用时。如:new Car().run();
  <2>作为实际参数进行传递时。
  (4)代码演示:
   public static void main(String[] args)
  {
       show(new Car());
  }
  public static void show(Car c)
  {
       c.num = 3;
       c.color = "black";
       c.run();
  } 

   (5)注意:
   <1>当对一个对象进行多个成员调用时,就必须给这个对象起个名字。
   <2>匿名对象作参数,show方法执行完,对象就释放内存。

二 封装 


  1封装概述 
 (1): 指隐藏对象的属性和实现细节,仅对外提供公共访问方式。
  (2)好处:
  将变化隔离
  便于使用
  提高重用性 
  提高安全性
  (3)封装原则 :
  将不需要的对外提供的内容都隐藏起来。
  把属性都隐藏,提供公共方法对其访问。
 (4) 函数,类,包 和框架 都是封闭体。

 2 封装private

(1) private关键字

private是一个权限修饰符。用于修饰成员(成员变量和成员函数,内部类)  被私有化的成员只有在本类中有效。

(2)要点说明:

<1>将成员变量私有化, 对外提供对应的set,get方法对其进行访问,提高对数据访问安全性。

<2>将属性私有化以后,类以外即使建立了对象也不能直接访问。

<3>私有仅仅是封装的一种表现形式,权限在访问不到的范围内都是封装。

<4>在访问方式中可加入逻辑判断语句,提高代码健壮性。


三 构造函数 


1 特点:

 (1) 函数名与类名相同

(2)不用定义返回值类型

(3)不可以写return语句

2 作用:给对象进行初始化

3 注意: 

(1)对象一建立就会调用 与之相对应的构造函数。若访问不到相应的构造函数,则对象不能建立。

(2)当一个类中没有定义构造函数时, 系统会默认给该类加入一个空参数的构造函数。

(3)在类中自定义了构造函数后,默认的构造函数就没有了。

(4)多个构造函数是以重载的形式存在的。

4.构造函数与一般函数的区别:

(1)构造函数是在对象一建立就运行,而一般方法是对象调用才运行。

 (2) 一个对象建立,构造函数只运行一次,而一般方法可多次被调用。

5 何时定义构造函数?

 (1) 当分析事物时, 该事物具备一些特性或行为,那么将这些内容定义在构造函数中。

6.构造代码块。

(1)作用:给对象进行初始化。对象一建立就运行,并且优先于构造函数执行。

(2)和构造函数的区别:

构造代码块是给所有对象进行统一初始化

构造函数是给所对应的对象进行初始化。

(3) 构造代码块中定义的是不同对象共性的初始化内容。


四 this 关键字 


1. this关键字 

this 是用于区*部变量和成员变量同名的情况。

this代表它所在函数所属对象的引用。

哪个对象在调用 this所在的函数,this就代表哪个对象。

2.this的应用 

(1) 当定义类中的功能时,该函数内部要用到调用 该的对象时, 这时用this来表示这个对象。

(2)但凡本类功能内部使用了本类对象,都使用this来表示。

3 代码示例:

class Person

{

private int age;

Person(int age)

{

this.age = age;

}

public boolean compare(Person p)

{

return this.age == p.age;

}
}

}


3.this在构造函数间的调用 

(1)this的调用 

<1>this语句: 用于构造函数之间进行互相调用 。

<2>this语句只能定义在构造函数的第一行,因为要初始化要先执行。


(2)this的两种用法:

<1>用于区分同名变量的情况。

<2>用于构造函数间调用 ,一般函数是不能直接调用构造函数的。

(3)代码演示:

class Person

{

private String name;

private int age;

Person()

{

System.out.println("hello");

}

Person(String name)

{

this();

this.name = name;

}

Person(String name,int age)

{

this(name);//构造函数间的相互调用 

this.age = age;

}
}

}


五 static 关键字


1.用法:

(1)是一个修饰符 ,用于修饰成员(成员变量和成员函数,内部类)

 (2) 当成员被静态修饰后,就多了一个调用方式,除了被对象调用外,还可以直接被类名调用,格式:类名.静态成员。

2 static 特点:

(1)随着类的加载而加载。

(2)优先于对象存在。

(3)被所有的对象所共享。

(4)可直接被类名调用 。

3.实例变量和类变更的区别:

(1)存放位置:

 类变量随着类的加载而存放于方法区中。

 实例变量随着对象的加载而存放于堆内存中。

(2)生命周期:

类变量生命周期长,随着类的消失而消失。

实例变量生命周期随着对象的消失而消失。

4.静态使用注意事项:

静态方法只能访问静态成员。非静态方法即可以访问静态也可以访问非静态。

静态方法只不可以定义this super关键字。因为静态优先于对象,所以静态方法中不可以出现this.

5 静态的利与弊:

(1)利:

节省空间。

可直接被类名调用。

(2)弊:

生命周期过长。

访问出现局限性。(静态虽好,只能访问静态)

6.什么时候使用静态

(1)什么时候定义静态变量(类变量)

当对象中出现共享数据时,该数据被静态所修饰。对象中的特有数据要定义成非静态存在于堆内存中。

(2)什么时候定义静态函数

当功能内部没有访问到非静态数据(对象的特有数据),那么该功能就可以定义成静态的。

7.静态代码块:

(1)格式:

static

{

静态代码块中的执行语句;

}

(2)特点:

随着类的加载而执行,只执行一次,并优先于主函数执行,用于给类进行初始化。


六 对象的初始化过程


Person p = new Person("lisi",20);该句话都做了什么?

(1)因为new用到了Person.class,所以会先找到Person.class文件并加载到内存中。

(2)执行该类中的static代码块,如果有的话,给Person.class类进行初始化。

(3)在堆内存中开辟空间,分配内存地址。

(4)在堆内存中建立对象的特有属性,并进行默认初始化。

(5)对属性进行显示初始化。

(6)对对象进行构造代码块初始化。

(7)对对象进行对应的构造函数初始化。

(8)将内存地址赋给栈内存中的引用变量p。


七 制作帮助文档


(1)帮助文档就是类的说明书,可帮助更好地使用类和程序。

(2)制作帮助文档使用的是javadoc.exe工具

F:\haima>javadoc -d myhelp -author -version ArrayTool.java

(3)注:

<1>凡是public修饰的功能都用文档注释来描述,因为都可以被文档注释工具所提取。

<2>只有public和protect修饰的类才可被提取生成文档。

<3>类中默认的构造函数的权限和所属类一致。且默认构造函数的权限是随着

类的变化而变化的。


八 单例设计模式


1.设计模式

(1)设计模式:解决某一类问题最行之有效的方法。java中有23种设计模式。

(2)单例设计模式:解决一个类在内存中只存在一个对象的问题。


2.单例设计的思想与步骤:

(1)将构造函数私有化。

(2)在类中创建一个本类对象。

(3)提供一个方法可以获取到该对象。


3.单例设计模式方式一:饿汉式(开发一般用这个)

代码示例:

class Single

{

private Single(){}

private static final Single s = new Single();

public static Single getInstance(){

return s;

}

}


4:单例设计模式方式二:懒汉式

 (1)对象是方法被调用时,才初始化 也叫对象的延迟加载。

Single类进内存,对象还没有存在。只有调用了getInstance方法才建立对象

代码示例:

class Single

{

private staitc Single s =  null;

        private Single(){}

public static Single getInstance()

        {

        if(s == nul)

s = new Single();

                  return s; 

       }

}


实例的延迟加载,多线程访问时会出现安全问题。使用判断优化如下:

public static Single getInstance()

{

if(s == null)

{

 synchronized(Single.class)

{

if(s == null)

                                s = new Single();

}

}

return s;

}

九.继承

1.概述  

 (1)例如 学生 和工人两个类   将这两个类中的共性内容抽取出来  定义成一个类 让学生和工人与单独
描述的这个类有关 抽取共性内容,建立父类。继承使用extends关键字.
 (2)作用

提高了代码的复用性。
让类与类之间产生了关系,有了这个关系,才有了多态的特性。

2 继承说明:

(1):  java语言中,java类只支持单继承,不支持多继承。但Java接口支持多继承。

(2)  父类中的private方法 子类不能使用 其它的属性和方法一般都可以在子类中调用 。

 3.子父类中变量的特点
(1)如果子类中出现非私有的同名成员变量时:
子类要访问本类中的变量,用this.
子类要访问父类中的同名变量,用super

(2)super
super的使用和this的使用几乎一致。
this代表的是本类对象的引用。
super代表的是父类对象的引用。

4.子父类中函数的特点---覆盖

(1)当子类出现和父类一模一样的函数时,子类对象调用该函数会运行子类函数的内容。
如同父类的函数被覆盖一样。这一特性叫函数的覆盖,也叫重写。
(2)子类继承父类,没必要定义新功能,只要保留父类的功能定义,并重写功能内容即可。


(3)子类覆盖父类,必须保证子类权限大于等于父类权限,才可以覆盖,否则编译失败。

(4)静态只能覆盖静态。

重载:只看同名函数的参数列表。
重写:子父类方法要一模一样。

5子父类中构造函数的特点---子类实例化过程

(1)在对子类对象进行初始化时,父类的构造函数也会运行。因为子类的构造函数
默认第一行有一条隐式语句super
(2)super():会访问父类中空参数的构造函数。而且子类中所有的构造函数默认
第一行都是super()。
(3)当父类中没有空参数的构造函数时,子类必须手动通过super或this语句形式
来指定要访问的构造函数。
(4)子类的构造函数第一行也可以手动指定this语句来访问本类中的构造函数。
子类中至少会有一个构造函数会访问父类中的构造函数。
(5)this()和super()不能同时出现在构造函数中,因为它们都要写在第一行。
因为初始化动作要先做,所以必须写第一行。