JavaSE-继承(包含Object类)
继承(包含Object类)
何为继承
在面向对象编程(OOP)中,继承是一种机制,它允许一个类(称为子类或派生类)继承另一个类(称为父类或基类)的属性和方法。继承提供了一种代码复用的方式,使得子类可以继承父类的公共属性和方法,而不需要重新编写相同的代码。
优点
代码复用
通过继承,可以在现有的类基础上创建新类,新类自动拥有父类的所有属性和方法,这样可以减少代码的重复编写。
易于维护和扩展
继承提供了一种层次结构,使得代码更加模块化,易于维护和扩展。如果需要修改某个功能,只需要在父类中修改,所有继承自该父类的子类都会受到影响。
缺点
紧密耦合
继承创建了类之间的强依赖关系,如果父类发生改变,可能会影响所有继承自该父类的子类。
缺乏灵活性
继承是静态的,一旦定义了继承关系,就很难改变。这限制了代码的灵活性。
常用的方法
在Java中,继承可以通过关键字extends
来实现。下面是一个简单的示例:
// 父类 class Animal { void eat() { System.out.println("动物吃东西"); } } // 子类 class Dog extends Animal { void bark() { System.out.println("狗叫"); } } public class TestInheritance { public static void main(String[] args) { Dog myDog = new Dog(); myDog.eat(); // 继承自Animal类的方法 myDog.bark(); // Dog类特有的方法 } }
Object类
在Java中,所有的类都隐式地继承自java.lang.Object
类,这是Java类层次结构的根类。即使在定义类时没有显式地指定父类,它也会默认继承自Object
类。
class MyClass { // ... } public class TestObject { public static void main(String[] args) { MyClass myObject = new MyClass(); // 可以使用Object类的方法 myObject.toString(); } }
Object类中的常用方法:
在Java中,Object
类是所有类的根类,它提供了一些常用的方法,这些方法在很多情况下都非常有用。以下是Object
类的一些常用方法及其简要说明:
-
equals(Object obj)
:检查传递给此方法的对象是否与该对象相等。默认行为是比较对象的引用,但通常需要根据类的属性重写这个方法。 -
hashCode()
:返回该对象的哈希码值。支持equals
方法的类通常也应该重写hashCode
方法,以维护equals
和hashCode
的一致性。 -
toString()
:返回该对象的字符串表示。通常需要重写这个方法以提供更有用的信息。 -
getClass()
:返回运行时类对象,这个类对象表示该对象的实际类。 -
notify()
和notifyAll()
:唤醒在此对象监视器上等待的单个或所有线程。 -
wait()
:导致当前线程等待,直到另一个线程调用此对象的notify()
或notifyAll()
方法。 -
wait(long timeout)
和wait(long timeout, int nanos)
:导致当前线程等待,直到另一个线程调用此对象的notify()
或notifyAll()
方法,或者超过指定的时间。
下面是一个示例,展示了如何使用这些方法:
class Person { private String name; private int age; public Person(String name, int age) { this.name = name; this.age = age; } @Override public boolean equals(Object obj) { if (this == obj) return true; if (obj == null || getClass() != obj.getClass()) return false; Person person = (Person) obj; return age == person.age && (name != null ? name.equals(person.name) : person.name == null); } @Override public int hashCode() { int result = name != null ? name.hashCode() : 0; result = 31 * result + age; return result; } @Override public String toString() { return "Person{" + "name='" + name + '\'' + ", age=" + age + '}'; } public static void main(String[] args) throws InterruptedException { Person person1 = new Person("Kimi", 30); Person person2 = new Person("Kimi", 30); System.out.println("person1 = " + person1); System.out.println("person2 = " + person2); System.out.println("Are person1 and person2 equal? " + person1.equals(person2)); System.out.println("Hash code of person1: " + person1.hashCode()); System.out.println("Hash code of person2: " + person2.hashCode()); // 获取类对象 System.out.println("Class of person1: " + person1.getClass().getName()); System.out.println("Class of person2: " + person2.getClass().getName()); } }
在这个例子中,我们重写了equals
、hashCode
和toString
方法,以便提供更有意义的行为。我们也展示了如何获取对象的类对象,并打印出它的名称。这个例子没有展示wait
、notify
和notifyAll
方法的使用,因为它们通常与多线程编程一起使用,涉及到更复杂的同步机制。
方法重写规则
方法重写(Override)是指子类中定义一个与父类中具有相同名称、参数列表的方法。这是实现多态的一种方式。
方法重写规则
- 方法名、参数列表和返回类型必须与父类中被重写的方法相同。
- 访问权限不能比父类中被重写的方法更严格。
- 不能重写父类中声明为
final
的方法。 - 如果父类中的方法被声明为
static
,则子类中的方法也必须是static
。
方法重写与方法重载的区别
- 方法重写:发生在子类和父类之间,要求方法名、参数列表相同,返回类型相同或兼容,访问权限相同或更宽松。
- 方法重载:发生在同一个类中,要求方法名相同,参数列表不同。
示例代码
class Parent { void show() { System.out.println("Parent show()"); } } class Child extends Parent { // 方法重写 void show() { System.out.println("Child show()"); } // 方法重载 void show(int num) { System.out.println("Child show(int num)"); } } public class TestOverride { public static void main(String[] args) { Child obj = new Child(); obj.show(); // 调用重写的方法 obj.show(10); // 调用重载的方法 } }
super
关键字的用法
super
关键字用于引用父类中的属性、方法和构造器。
示例代码
class Parent { String name = "Parent"; void show() { System.out.println("Parent show()"); } } class Child extends Parent { String name = "Child"; void show() { super.show(); // 调用父类的show方法 System.out.println("Child show(), name = " + name); } } public class TestSuper { public static void main(String[] args) { Child obj = new Child(); obj.show(); } }
final
关键字的用法
final
关键字可以用于修饰类、方法和变量。
- final类:不能被继承。
- final方法:不能被重写。
- final变量:一旦赋值后,其值不能被改变。
示例代码
final class FinalClass { // ... } class MyClass { final void show() { // ... } } public class TestFinal { public static void main(String[] args) { final int num = 10; // final变量 // num = 20; // 编译错误:不能为final变量赋值 } }
通过上述内容,你应该对继承有了基本的了解,包括它的概念、优点、缺点、方法重写规则以及super
和final
关键字的用法。希望这些示例代码能帮助你更好地理解这些概念。
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· CSnakes vs Python.NET:高效嵌入与灵活互通的跨语言方案对比
· 【.NET】调用本地 Deepseek 模型
· Plotly.NET 一个为 .NET 打造的强大开源交互式图表库
· 上周热点回顾(2.17-2.23)
· 如何使用 Uni-app 实现视频聊天(源码,支持安卓、iOS)