这些问题在ebay面试的时候被问了若干编 第一,谈谈final, finally, finalize的区别。 final是修饰符 1.如果一个类被声明为final,意味着它不能再派生出新的子类,不能作为父类被继承。因此一个类不能既被声明为 abstract的,又被声明为final的。 2.变量或方法声明为final,可以保证它们在使用中不被改变。被声明为final的变量必须在声明时给定 初值,而在以后的引用中只能读取,不可修改。被声明为final的方法也同样只能使用,不能重载 根据提供的文件信息,本文将对其中提及的部分经典Java面试题进行详细解析,旨在帮助读者更好地理解和掌握这些重要的Java概念。 ### 1. final, finally, finalize 的区别 #### final `final` 是 Java 中的一个关键字,用作修饰符,主要用途有两个: 1. **类级别的修饰**:当一个类被声明为 `final` 时,意味着这个类不能再被继承,即无法创建该类的子类。由于 `final` 类不能被继承,因此它也不能同时被声明为 `abstract`。 **示例代码**: ```java public final class MyClass { // ... } ``` 2. **成员变量和方法级别的修饰**:当成员变量或方法被声明为 `final` 时,可以确保它们在程序运行过程中不会被修改。对于 `final` 变量来说,一旦初始化后其值就不能改变;对于 `final` 方法,其他类无法对其进行重写。 **示例代码**: ```java public class MyClass { private final int myFinalVariable = 10; public final void myFinalMethod() { // ... } } ``` #### finally `finally` 块用于异常处理结构中,确保无论是否发生异常,都会执行其中的代码。当程序中出现异常,并且通过 `try-catch` 结构捕获异常时,即使异常没有被捕获,`finally` 块中的代码也会被执行。这意味着 `finally` 块是一定会被执行的,无论是否有异常发生。 **示例代码**: ```java public void myMethod() { try { // 可能会抛出异常的代码 } catch (Exception e) { // 处理异常 } finally { // 这里的代码一定会被执行 } } ``` #### finalize `finalize` 是一个方法,定义于 `Object` 类中,通常用于对象销毁之前释放资源(例如关闭文件等)。当垃圾回收器准备回收一个对象时,会调用该对象的 `finalize` 方法来完成最后的清理工作。需要注意的是,`finalize` 方法并不总是会被调用,而且它的执行时机也不确定。 **示例代码**: ```java protected void finalize() throws Throwable { // 进行资源清理操作 super.finalize(); } ``` ### 2. Anonymous Inner Class **定义**:匿名内部类是在声明类的同时创建其实例的一种方式,它没有显式的名字,只能在一个表达式中定义。匿名内部类主要用于简化代码,尤其是在实现接口或者继承类时使用较少的代码。 **特点**: - 不需要名称 - 必须继承一个类或者实现一个接口 - 可以访问外部类的所有成员变量(包括私有的),但不能声明静态成员 - 在构造匿名内部类时,可以直接提供实现接口或者继承类的方法 ### 3. Static Nested Class vs Inner Class **Static Nested Class(静态嵌套类)**:也称为静态内部类,是一种特殊的内部类,它可以通过外部类名直接访问,而无需创建外部类的实例。静态嵌套类的特点是它可以包含静态成员,但不能访问外部类的非静态成员。 **Inner Class(内部类)**:通常指非静态内部类,它是定义在另一个类中的类。与静态嵌套类不同,非静态内部类可以访问外部类的所有成员,包括私有成员。但创建非静态内部类实例时,需要先有一个外部类的实例。 ### 4. Collection Framework **概述**:Java Collection Framework 提供了一组接口和实现类,用于存储和管理对象集合。主要包括以下核心接口: - `Collection`:所有集合类的根接口。 - `List`:有序集合,允许重复元素。 - `Set`:不允许重复元素的集合。 - `Map`:键值对集合。 **常用实现类**: - `ArrayList`:基于数组实现的 List。 - `LinkedList`:基于链表实现的 List。 - `HashSet`:基于哈希表实现的 Set。 - `TreeSet`:基于红黑树实现的 Set,可自然排序。 - `HashMap`:基于哈希表实现的 Map。 - `TreeMap`:基于红黑树实现的 Map,可自然排序。 ### 5. assert 断言 **概述**:`assert` 语句用于开发阶段测试代码,它会在条件不满足时抛出 `AssertionError`。断言可以用来检查程序的假设条件是否成立,例如参数的有效性、不变量等。 **语法**: ```java assert <expression1>; assert <expression1> : <expression2>; ``` - `<expression1>`:表示断言的条件。 - `<expression2>`:表示当断言失败时要输出的信息,默认为空字符串。 **启用和禁用断言**: - 编译时:使用 `-source 1.4` 来编译代码以启用断言支持。 - 运行时:使用 `-enableassertions` 或 `-ea` 来全局启用断言,使用 `-disableassertions` 或 `-da` 来禁用断言,使用 `-esa` 或 `-dsa` 来启用或禁用特定包的断言。 ### 6. Garbage Collection (GC) **概述**:垃圾收集(GC)是 Java 自动内存管理的关键特性之一,它负责自动释放不再使用的对象所占用的内存空间,从而避免内存泄漏。Java 使用多种算法和技术来实现 GC,如分代收集和并发标记-清除算法。 **触发 GC**: - 直接调用 `System.gc()` 或 `Runtime.getRuntime().gc()` 可以请求执行 GC,但这不是最佳实践,因为 JVM 可能会选择忽略这些请求。 - JVM 自动执行 GC,通常发生在对象分配失败(堆内存不足)或内存碎片过多时。 ### 7. String 和 StringBuilder/StringBuffer **String**:在 Java 中,`String` 类代表不可变字符序列。这意味着一旦创建了一个 `String` 对象,其内容就不能更改。`String` 类实现了 `Serializable` 和 `Comparable` 接口,使得字符串可以被序列化以及比较大小。 **StringBuilder/StringBuffer**:这两个类提供了可变的字符序列。`StringBuilder` 是线程不安全的,适用于单线程环境;而 `StringBuffer` 是线程安全的,适用于多线程环境。在构建或修改大量文本时,使用 `StringBuilder` 或 `StringBuffer` 能够提高性能。 ### 8. Math.round() **Math.round() 方法**:用于将浮点数四舍五入到最接近的整数。对于正数,如果小数部分大于等于 0.5,则向上取整;小于 0.5,则向下取整。对于负数,逻辑相同,但取整方向相反。 **示例**: - `Math.round(11.5)` 返回 `12`(long 类型) - `Math.round(-11.5)` 返回 `-11`(long 类型) ### 9. short 类型操作 **问题**:`short s1 = 1; s1 = s1 + 1;` 为什么会出现编译错误? **解释**:Java 中 `short` 类型变量的运算结果默认为 `int` 类型,因此在执行 `s1 + 1` 时,结果是一个 `int` 类型值。为了将 `int` 类型赋值给 `short` 类型变量 `s1`,需要显式地进行类型转换,即 `s1 = (short)(s1 + 1);`。 ### 10. sleep() 和 wait() **sleep() 方法**:`Thread.sleep(long millis)` 使当前线程暂停执行指定的时间,单位为毫秒。在此期间,线程会放弃 CPU 时间片,但不会释放锁。`sleep()` 方法是静态方法,位于 `Thread` 类中。 **wait() 方法**:`wait()` 方法位于 `Object` 类中,用于让持有对象锁的线程进入等待状态。当调用 `wait()` 方法时,线程会释放该对象上的锁,直到其他线程调用该对象的 `notify()` 或 `notifyAll()` 方法唤醒它。 ### 11. Java 是否支持 goto? **Java 不支持传统的 goto 关键字**。尽管 Java 最初设计时考虑过加入 goto,但最终决定将其从语言规范中移除,因为它可能导致代码难以阅读和维护。然而,在 Java 中可以使用 `break` 和 `continue` 关键字加上标签来模拟类似 goto 的行为。 ### 12. String.length() **String 类**:`String` 类代表不可变的字符序列,它提供了一系列方法用于操作字符串。`String` 类的 `length()` 方法返回字符串中字符的数量,即字符串的长度。 **示例代码**: ```java String str = "Hello, World!"; int length = str.length(); // length 的值为 13 ``` ### 13. Overload 与 Override **Overload(重载)**:指同一个类中可以有多个同名的方法,但参数列表必须不同。重载允许程序员使用相同的名称定义不同的方法版本,从而提高代码的可读性和重用性。 **Override(覆盖)**:指子类重新定义父类的方法。覆盖要求子类的方法必须与父类的方法具有相同的名称、参数列表和返回类型。此外,子类方法的访问级别不能低于父类方法。 ### 14. Set 集合 **Set 接口**:`Set` 是 `Collection` 接口的子接口,它不允许包含重复元素。在 `Set` 中,每个元素都是唯一的,即使多次添加相同的元素,实际上只保存一份。 **实现类**: - `HashSet`:基于哈希表实现的 `Set`,插入顺序不保留,查询效率高。 - `LinkedHashSet`:基于哈希表和双向链表实现的 `Set`,插入顺序保持不变。 - `TreeSet`:基于红黑树实现的 `Set`,可以按自然顺序或自定义比较器排序元素。 **元素相等性**: - `Set` 集合通过 `equals()` 方法判断元素是否相等。 - 默认情况下,元素相等性由对象的 `equals()` 方法决定。因此,如果要自定义元素的相等性标准,需要覆盖 `equals()` 方法。 ### 15. RuntimeException **RuntimeException**:是非检查异常的基类,表示在运行时可能会发生的异常情况。与 `Exception` 不同,`RuntimeException` 及其子类不需要在方法签名中声明抛出。常见的 `RuntimeException` 子类包括但不限于: - `ArithmeticException`:算术运算异常,如除零。 - `ArrayStoreException`:试图向数组中存储不兼容类型的元素时抛出。 - `BufferOverflowException`:缓冲区溢出异常。 - `BufferUnderflowException`:缓冲区欠溢出异常。 - `CannotRedoException`:无法重做异常。 - `CannotUndoException`:无法撤销异常。 - `ClassCastException`:类型转换异常。 - `CMMException`:色彩管理模块异常。 - `ConcurrentModificationException`:并发修改异常。 - `DOMException`:文档对象模型操作异常。 - `EmptyStackException`:空栈异常。 - `IllegalArgumentException`:非法参数异常。 以上对这些经典 Java 面试题进行了详细的解答,希望能帮助读者加深对 Java 的理解。
- 粉丝: 1
- 资源: 7
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助