Skip to content

Java面向对象面试题

1. 面向对象的基本概念

问题:什么是面向对象编程?

答案: 面向对象编程(Object-Oriented Programming,OOP)是一种编程范式,它将现实世界中的实体抽象为对象,通过对象之间的交互来实现程序功能。面向对象编程的核心思想是封装、继承和多态。

2. 面向对象的四大特性

问题:面向对象的四大特性是什么?

答案

  • 封装:将对象的属性和行为封装在一起,对外提供统一的接口,隐藏内部实现细节。
  • 继承:子类继承父类的属性和方法,实现代码复用。
  • 多态:同一个方法调用在不同对象上会产生不同的行为。
  • 抽象:将具有共同特征的对象抽象为类,定义抽象方法和抽象类。

3. 封装

问题:什么是封装?如何实现封装?

答案

  • 封装:将对象的属性和行为封装在一起,对外提供统一的接口,隐藏内部实现细节。
  • 实现封装
    • 使用private修饰符修饰属性。
    • 提供public的getter和setter方法来访问和修改属性。

示例

java
public class Person {
    private String name;
    private int age;
    
    public String getName() {
        return name;
    }
    
    public void setName(String name) {
        this.name = name;
    }
    
    public int getAge() {
        return age;
    }
    
    public void setAge(int age) {
        if (age >= 0) {
            this.age = age;
        }
    }
}

4. 继承

问题:什么是继承?继承的优缺点是什么?

答案

  • 继承:子类继承父类的属性和方法,实现代码复用。
  • 优点
    • 代码复用,减少重复代码。
    • 提高代码的可维护性。
    • 便于扩展功能。
  • 缺点
    • 增加了类之间的耦合度。
    • 可能导致继承层次过深,难以理解和维护。

5. 多态

问题:什么是多态?如何实现多态?

答案

  • 多态:同一个方法调用在不同对象上会产生不同的行为。
  • 实现多态的条件
    • 继承关系。
    • 方法重写。
    • 父类引用指向子类对象。

示例

java
class Animal {
    void makeSound() {
        System.out.println("Animal makes sound");
    }
}

class Dog extends Animal {
    @Override
    void makeSound() {
        System.out.println("Dog barks");
    }
}

class Cat extends Animal {
    @Override
    void makeSound() {
        System.out.println("Cat meows");
    }
}

public class Test {
    public static void main(String[] args) {
        Animal animal1 = new Dog();
        Animal animal2 = new Cat();
        
        animal1.makeSound(); // 输出:Dog barks
        animal2.makeSound(); // 输出:Cat meows
    }
}

6. 抽象类和接口

问题:抽象类和接口的区别是什么?

答案

特性抽象类接口
关键字abstract classinterface
构造方法
成员变量可以有实例变量只能有常量(public static final)
方法可以有抽象方法和具体方法只能有抽象方法(Java 8之前),Java 8及以后可以有默认方法和静态方法
继承只能单继承可以多实现
访问修饰符可以有各种访问修饰符默认为public

7. 抽象方法和具体方法

问题:什么是抽象方法?什么是具体方法?

答案

  • 抽象方法:没有实现体的方法,使用abstract关键字修饰,必须在抽象类或接口中声明。
  • 具体方法:有实现体的方法。

8. 接口的作用

问题:接口的作用是什么?

答案

  • 定义规范和契约,规定实现类必须实现的方法。
  • 实现多继承,一个类可以实现多个接口。
  • 解耦,提高代码的灵活性和可扩展性。

9. 内部类

问题:Java中有哪些类型的内部类?

答案

  • 成员内部类:定义在类内部的非静态类。
  • 静态内部类:定义在类内部的静态类。
  • 局部内部类:定义在方法内部的类。
  • 匿名内部类:没有名称的内部类,通常用于创建接口或抽象类的实例。

10. 匿名内部类

问题:什么是匿名内部类?如何使用?

答案

  • 匿名内部类:没有名称的内部类,通常用于创建接口或抽象类的实例。
  • 使用方式

示例

java
interface Greeting {
    void sayHello();
}

public class Test {
    public static void main(String[] args) {
        Greeting greeting = new Greeting() {
            @Override
            public void sayHello() {
                System.out.println("Hello!");
            }
        };
        greeting.sayHello();
    }
}

11. 静态内部类

问题:什么是静态内部类?与成员内部类有什么区别?

答案

  • 静态内部类:定义在类内部的静态类。
  • 区别
    • 静态内部类不依赖于外部类的实例,可以直接通过外部类名访问。
    • 成员内部类依赖于外部类的实例,需要通过外部类实例访问。
    • 静态内部类只能访问外部类的静态成员,不能访问非静态成员。
    • 成员内部类可以访问外部类的所有成员。

12. 局部内部类

问题:什么是局部内部类?

答案: 局部内部类是定义在方法内部的类,只能在方法内部使用。

示例

java
public class Test {
    public void method() {
        class LocalClass {
            void print() {
                System.out.println("Local class");
            }
        }
        
        LocalClass localClass = new LocalClass();
        localClass.print();
    }
    
    public static void main(String[] args) {
        Test test = new Test();
        test.method();
    }
}

13. 方法重写和方法重载的区别

问题:方法重写和方法重载的区别是什么?

答案

特性方法重写方法重载
定义子类重新实现父类的方法在同一个类中,有多个方法名相同但参数列表不同的方法
方法名相同相同
参数列表相同不同
返回值类型相同(或子类类型)可以相同也可以不同
访问修饰符不能比父类更严格可以相同也可以不同
异常不能抛出比父类更多的异常可以相同也可以不同

14. 构造方法的继承

问题:构造方法可以被继承吗?

答案: 构造方法不能被继承。子类可以通过super关键字调用父类的构造方法。

15. super关键字的使用

问题:super关键字有什么作用?

答案

  • 调用父类的构造方法。
  • 访问父类的成员变量。
  • 调用父类的方法。

示例

java
class Parent {
    int age = 40;
    
    Parent() {
        System.out.println("Parent constructor");
    }
    
    void print() {
        System.out.println("Parent print");
    }
}

class Child extends Parent {
    int age = 20;
    
    Child() {
        super(); // 调用父类构造方法
        System.out.println("Child constructor");
    }
    
    void print() {
        super.print(); // 调用父类方法
        System.out.println("Child print");
        System.out.println("Parent age: " + super.age); // 访问父类成员变量
        System.out.println("Child age: " + this.age); // 访问子类成员变量
    }
}

public class Test {
    public static void main(String[] args) {
        Child child = new Child();
        child.print();
    }
}

16. this关键字的使用

问题:this关键字有什么作用?

答案

  • 指代当前对象。
  • 访问当前对象的成员变量。
  • 调用当前对象的方法。
  • 调用当前类的构造方法。

示例

java
class Person {
    private String name;
    private int age;
    
    Person() {
        this("Unknown", 0); // 调用当前类的另一个构造方法
    }
    
    Person(String name, int age) {
        this.name = name; // 访问当前对象的成员变量
        this.age = age;
    }
    
    void print() {
        System.out.println("Name: " + this.name); // 访问当前对象的成员变量
        System.out.println("Age: " + this.age);
    }
}

public class Test {
    public static void main(String[] args) {
        Person person = new Person("John", 30);
        person.print();
    }
}

17. final关键字的使用

问题:final关键字有什么作用?

答案

  • final变量:值不能改变的变量。
  • final方法:不能被子类重写的方法。
  • final类:不能被继承的类。

18. static关键字的使用

问题:static关键字有什么作用?

答案

  • 静态变量:属于类,所有实例共享同一个变量值。
  • 静态方法:属于类,可以直接通过类名调用,不需要创建对象。
  • 静态代码块:在类加载时执行,只执行一次。
  • 静态内部类:不依赖于外部类的实例,可以直接访问外部类的静态成员。

19. 面向对象设计原则

问题:面向对象设计的基本原则有哪些?

答案

  • 单一职责原则:一个类只负责一个功能领域的职责。
  • 开闭原则:对扩展开放,对修改关闭。
  • 里氏替换原则:子类可以替换父类,而不影响程序的正确性。
  • 依赖倒置原则:依赖于抽象,而不是具体实现。
  • 接口隔离原则:使用多个专门的接口,而不是一个统一的接口。
  • 迪米特法则:一个对象应该对其他对象有最少的了解。
  • 合成复用原则:优先使用组合,而不是继承。

20. 设计模式

问题:什么是设计模式?常见的设计模式有哪些?

答案

  • 设计模式:在软件开发中,针对特定问题的解决方案。
  • 常见的设计模式
    • 创建型模式:单例模式、工厂模式、抽象工厂模式、建造者模式、原型模式。
    • 结构型模式:适配器模式、桥接模式、装饰器模式、组合模式、外观模式、享元模式、代理模式。
    • 行为型模式:策略模式、模板方法模式、观察者模式、迭代器模式、责任链模式、命令模式、备忘录模式、状态模式、访问者模式、中介者模式、解释器模式。