
Welcome to object -oriented programming storage with Java ! It provides a comprehensive resource to explore and learn object -oriented programming through Java language.
Object -oriented programming (OOP - Oop - Oop -oriented Programming) is a popular programming model that is widely used in software development. It is based on the concepts of "objects", which are entities that combine both data (attributes) and methods (behaviors). OOP focuses on software design based on interactive objects, instead of the process and logic as in the procedural programming programming.
Object -oriented programming is based on 4 basic principles, namely: packaging, inheritance, polymorphism, and abstract. Each of these principles provide an approach to solve problems in software development and help manage source code more effectively.
1. Encapsulation : This is the concept of hiding the internal deployment details of the object, preventing users directly access the data inside. Packaging helps protect the data and behavior of the object from unwanted intervention and provides a unified interface to interact with the object.
// Lớp Employee (Nhân viên) chứa các thuộc tính: tên, tuổi, lương
public class Employee {
// Các biến dữ liệu riêng tư để ngăn chặn truy cập trực tiếp từ bên ngoài lớp
private String name ;
private int age ;
private double salary ;
// Constructor (hàm tạo) để khởi tạo các giá trị của đối tượng
public Employee ( String name , int age , double salary ) {
this . name = name ;
this . age = age ;
this . salary = salary ;
}
// Các phương thức getter để truy cập các biến dữ liệu
public String getName () {
return name ;
}
public int getAge () {
return age ;
}
public double getSalary () {
return salary ;
}
// Các phương thức setter để cập nhật giá trị của các biến dữ liệu
public void setName ( String name ) {
this . name = name ;
}
public void setAge ( int age ) {
this . age = age ;
}
public void setSalary ( double salary ) {
this . salary = salary ;
}
}
// Lớp Main để thực thi mã
public class Main {
public static void main ( String [] args ) {
// Tạo đối tượng của lớp Employee
Employee emp = new Employee ( "John Doe" , 30 , 50000 );
// Truy cập và cập nhật thông qua các phương thức getter và setter
System . out . println ( "Employee name: " + emp . getName ());
emp . setSalary ( 55000 );
System . out . println ( "Updated salary: " + emp . getSalary ());
}
} In this example, the variables name , age , and salary are marked as private , which means they cannot be directly accessed from the outside of the Employee . Instead, getName() , getAge() , getSalary() , setName() , setAge() , and setSalary() are provided to access and update the value of these variables, ensuring packaging.
2. Inheritance (Inheritance): Inheritance allows a new layer to inherit properties and methods from an existing layer. This new layer can add or modify the inheritance components to meet its own needs, helping to reuse and expand the source code effectively.
// Lớp cơ sở (hay lớp cha): Employee
public class Employee {
private String name ;
private int age ;
// Constructor của lớp Employee
public Employee ( String name , int age ) {
this . name = name ;
this . age = age ;
}
// Getter và Setter
public String getName () {
return name ;
}
public void setName ( String name ) {
this . name = name ;
}
public int getAge () {
return age ;
}
public void setAge ( int age ) {
this . age = age ;
}
// Phương thức để hiển thị thông tin
public void displayInfo () {
System . out . println ( "Name: " + name + ", Age: " + age );
}
}
// Lớp dẫn xuất (hay lớp con): Manager kế thừa từ Employee
public class Manager extends Employee {
private double salary ;
// Constructor của lớp Manager
public Manager ( String name , int age , double salary ) {
super ( name , age ); // Gọi constructor của lớp cơ sở (lớp cha)
this . salary = salary ;
}
// Phương thức mới của lớp Manager
@ Override
public void displayInfo () {
// Gọi phương thức displayInfo của lớp cơ sở (lớp cha)
super . displayInfo ();
System . out . println ( "Salary: " + salary );
}
}
public class Main {
public static void main ( String [] args ) {
// Tạo đối tượng Manager
Manager manager = new Manager ( "Alice Johnson" , 42 , 75000 );
manager . displayInfo (); // Hiển thị thông tin của Manager
}
}Employee class is a base class, containing basic information like name and age.Manager layer is the derivative class from Employee and adds the salary attribute.Manager layer uses keyword extends to inherit from the Employee class. Manager 's constructor called super(name, age) ; To initialize the properties inherited from the Employee class.displayInfo() method is overwritten in the Manager class to add more information about the salary, and call displayInfo() method of the base class to display the basic information.3. Polymorphism : polymorphism is the ability whereby different classes can be used through the same interface. The method can be defined in a base layer and are replaced by the methods of the same name in the derivative classes, allowing the objects to be processed through the common interface without knowing their specific data type.
In Java, the polymorphism is expressed through the method of overhod overliding and recharging the method (method overloading).
class Animal {
void speak () {
System . out . println ( "Animal speaks" );
}
}
// Lớp Dog (chó) kế thừa lớp Animal (động vật)
class Dog extends Animal {
// Lớp Dog ghi đè phương thức speak() của lớp cha
@ Override
void speak () {
System . out . println ( "Dog barks" );
}
}
// Lớp Cat (mèo) kế thừa lớp Animal (động vật)
class Cat extends Animal {
// Lớp Dog ghi đè phương thức speak() của lớp cha
@ Override
void speak () {
System . out . println ( "Cat meows" );
}
}
public class Main {
public static void main ( String [] args ) {
Animal myAnimal = new Animal ();
Animal myDog = new Dog ();
Animal myCat = new Cat ();
myAnimal . speak (); // Prints "Animal speaks"
myDog . speak (); // Prints "Dog barks"
myCat . speak (); // Prints "Cat meows"
}
} In this example, the speak() method is overwritten in the Dog and Cat layers. When calling the speak() method on the object of the child, Java determines which method will be called at the time of running, depending on the type of object that the reference variable comes.
class Printer {
// In chuỗi
void print ( String data ) {
System . out . println ( "String: " + data );
}
// In số nguyên
void print ( int data ) {
System . out . println ( "Integer: " + data );
}
// In số thực
void print ( double data ) {
System . out . println ( "Double: " + data );
}
}
public class Main {
public static void main ( String [] args ) {
Printer printer = new Printer ();
// Gọi phương thức print nạp chồng
printer . print ( "Hello, World!" );
printer . print ( 123 );
printer . print ( 98.76 );
}
}Printer class has three versions of the print method, each processing a specific data type: String , int , and double .print method, Java will determine the appropriate version based on the data type of the transmission argument.The polymorphism is also clearly expressed through the mechanism of using interface. Interface in Java is a way to achieve a higher polymorphism, allowing a layer to deploy many interfaces and an interface that can be deployed by different layers.
Suppose we have an interface CanFly and two layers Bird and Airplane both implement this interface:
interface CanFly {
void fly ();
}
class Bird implements CanFly {
public void fly () {
System . out . println ( "The bird flaps its wings to fly." );
}
}
class Airplane implements CanFly {
public void fly () {
System . out . println ( "The airplane turns on its engines to fly." );
}
}
public class TestPolymorphism {
public static void main ( String [] args ) {
CanFly myBird = new Bird ();
CanFly myAirplane = new Airplane ();
myBird . fly (); // Output: The bird flaps its wings to fly.
myAirplane . fly (); // Output: The airplane turns on its engines to fly.
}
}CanFly defines the fly() method without providing the body body.Bird and Airplane deploy the fly() method in their own way.myBird and myAirplane objects are referenced through the interface CanFly , and when calling the fly() method, polymorphism allows us not to care about the object of the object; We only know that they can fly.4. Abstraction : abstract allows programmers to focus on what an object does without care about how to do it. It creates a base class that describes a general interface that the derivative classes will implement, simplifying the management of the system's complexity.
In Java, abstract can be done in two ways:
Abstract class is an object that cannot be created and can contain abstract methods without body.
abstract class Animal {
// Phương thức trừu tượng
abstract void makeSound ();
// Phương thức bình thường
void breathe () {
System . out . println ( "Breathing..." );
}
}
class Dog extends Animal {
// Triển khai phương thức trừu tượng trong lớp con
void makeSound () {
System . out . println ( "Bark" );
}
}
public class Main {
public static void main ( String [] args ) {
Animal myDog = new Dog ();
myDog . makeSound (); // In ra "Bark"
myDog . breathe (); // In ra "Breathing..."
}
}Animal is an abstract layer with abstract methods makeSound() .Dog is an inherited class from Animal and must provide specific deployment for the abstract method makeSound() .Interface (interface) can only contain abstract methods without deployment.
interface Vehicle {
void start ();
void stop ();
}
class Car implements Vehicle {
public void start () {
System . out . println ( "Car starting" );
}
public void stop () {
System . out . println ( "Car stopping" );
}
}
class Bike implements Vehicle {
public void start () {
System . out . println ( "Bike starting" );
}
public void stop () {
System . out . println ( "Bike stopping" );
}
}
public class Main {
public static void main ( String [] args ) {
Vehicle myCar = new Car ();
Vehicle myBike = new Bike ();
myCar . start (); // In ra "Car starting"
myCar . stop (); // In ra "Car stopping"
myBike . start (); // In ra "Bike starting"
myBike . stop (); // In ra "Bike stopping"
}
} Here, Vehicle is an interface defining two abstract methods: start() and stop() . Car and Bike layers deploy this interface and provide specific deployment for each method.
Similarity:
Differences:
| Abstract class | Interface | |
|---|---|---|
| Purpose | - Often used when sub -classes have many common functions and need a common place to place the code that can be reused. - Help define a basic pattern for the sub -layer, make sure all the sub -class inherits it to follow a common design. | - Often used to define a contract for a function without caring. - Ideal for functions that can be implemented very different. - Good for the definition of gathering methods that a class can perform. |
| Deployment | - Can contain both abstract methods (no body) and non -abstract methods (with body). - Abstract classes can also contain data fields and constructors. | - Initially, it only allows the definition of abstract methods without body. - From Java 8 onwards, the interface also allows the definition of body methods through Default Methods and Static Methods. |
| Multi -inheritance | - A class can only inherit from a single abstract layer. - This limits the flexibility of multi -inheritance as in the interface. | - Java allows a layer to perform multiple interfaces at the same time, providing a multi -inheritance form. |
| Jaw | - There may be constraints, helping to set the initial conditions for the class. | - There is no constructor. |
| Data field | - Unlike the interface, abstract classes may have data fields that are not statics and final. - The sub -layer may have separate attributes inherited from the abstract layer. | - The interface does not support the data field is not static and final. - All variables declared in the interface are automatically considered the public static final. |
Object -oriented programming brings many outstanding advantages in software development, making it one of the main design and programming models in the information technology industry. Here are the advantages of it:
Reusing code : OOP allows programmers to reuse the source code through the inheritance mechanism. The child's layer can inherit the features from the father class without rewriting that code. This helps reduce programming work, minimize potential errors and speed up software development.
Easy to maintain and fix errors : The packaging structure in OOP helps hide the deployment details, only providing the interface (interface) necessary for users. This makes the system maintenance and update easier, because changing inside a object does not affect other objects.
Practical modeling : OOP allows programming to model real entities in the form of software objects, making the source code easier to understand and manage. The use of objects such as performing data and behaviors in the real world helps develop software to become more intuitive and closer to the programmer.
Expansion : Thanks to the ability to inherit and pack, OOP is easy to expand. A new layer can be created with inheritance from one or more layers that exist without affecting those layers. This helps the system grow flexibly and adapt to new needs quickly.
Security : Packaging not only helps hide the implementation details but also provides a security layer. Data inside an object is protected from external direct access, ensuring the integrity and safety of data.
Java is one of the most popular programming languages used to teach object -oriented programming for plausible reasons.
Java is a pure object -oriented language , meaning everything in Java is object or class. Concepts such as inheritance, packaging, polymorphism, and abstract are completely built into language. This helps learners easily access and practice OOP principles naturally during programming.
Java has a clear and easy -to -understand syntax. Java's syntax is based on C/C ++, but has removed some complex features such as direct cursor, making it an ideal language to teach beginners. The elimination of these complex features helps learners focus on understanding the core concepts of OOP without being bogged down in confusing details.
Java is an independent language foundation , can run on any operating system with Java (JVM) virtual machine. This means that Java programs can develop and implement consistently on different platforms without changing the code. This flexibility is ideal for the learning environment, where students and teachers can use a variety of hardware and software.
While using this archive for learning, you should follow the arrangement principle mentioned below. Read the items in accordance with the rules from top to bottom, the first parts will be the basis of the next content. Particularly for the appendix you can refer at any time, it contains some books I use for designing this archive.
To synchronize and be easy to control, the main layer contains the main method to execute the code as the same as the lesson content. Other classes in the lesson to illustrate. For example, the lesson about interface is in
Interface.javahas classes:Movable,Trackable,Drone,Interface, theMovable,Trackable,Droneclasses have the effect of interpreting for lesson knowledge, andInterfaceclasses to execute code from the previous classes it.
This item is almost the same order as my storage: data structure and algorithm using C/C ++ , except that is written in Java language. There will be some differences between the two languages, readers can compare them themselves.
Java is both a programming language and a translation (and interpreted . In Java, the source code is translated into bytecode, which is simple binary indicators that work like computer code for computers. However, unlike C or C ++, Java's bytecode is not the native machine code for any specific processor but for a Java (JVM) virtual machine, a common platform for all systems.
This bytecode was then translated and executed by the Java virtual machine as if it was a native machine code. JVM works like an active operating system in managing memory and processing commands, ensuring the safety and mobile of the code. All characteristics of the Java language are clearly defined, regardless of the specific system of the basic system, helping Java to be able to run homogeneous on many different platforms without code editing.
JVM provides a safe enforcement environment, where it performs functions similar to an operating system. It manages memory, executing commands based on stacks, and processing water types. This minimizes security risks and increases the stability of the application.
Whether it looks similar to C and C ++ in terms of syntax, Java is not a direct descendant of C or the next version of C ++. Java has more in common with dynamic languages like Smalltalk and LISP rather than C. The similarity only stops at the external syntax like using many braces and semicolons. Java inherits C's philosophy of a good language that should be compact, easy to remember but expand vocabulary through Java class packages.
The script languages such as Perl, Python and Ruby are very popular because they are suitable for safe and networked applications. However, most script languages are not designed for serious large -scale programming. They are often not suitable for large or complex projects because of the loose program structure and simple data system.
Java provides a safe platform to develop higher -level frameworks and even other languages, combining simplicity and features of Java that allows rapid and easy development of applications. Java has also learned from the features of Smalltalk and improves them, especially in the use of the BYTecode test set to ensure the accuracy of the campaign code, helping to improve performance and ensure safety than Smalltalk.
Java is designed to be a safe language, not only against software errors but also common problems in design and programming. Java offers many protective layers, from the safety test of the code before running to the way that the class loader is loaded, a bytecode load mechanism of the Java interpretation, creating a "wall" around unreliable classes. These features are the foundation for high -level security policies, allowing or not allowing various types of activities on each application.
Java starts from a "white board" and therefore can avoid complex or controversial features in other languages. For example, Java does not allow programmers to regenerate operators (such as + Hay -), no money processing money like Macros or #Define Statements, things that are often used in other languages to support dependence on the platform.
Java also provides a clear package structure to organize class files, helping the compilation process to handle some functions of the traditional make -made tool effectively. All data type information is preserved in the compiled Java classes, without the need for excess source title files as in C/C ++. This makes Java code easier to read and less context.
Java only supports the inheritance (each class has only one "father" class) but allows inheritance of many interfaces. The interface in Java, similar to the abstract layer in C ++, identifies the behavior of an object without defending its execution. This is a powerful mechanism that allows the developer to define an "contract" of the object's behavior that can be used and referenced independently to any specific object execution.
Java eliminates the use of cursors that can refer to any memory area and add automatically garbage collection and high level segment. These features help eliminate many problems related to safety, conversion and optimization that other languages often encounter. In Java, no longer used subjects will automatically recover memory, minimize manual memory management errors.
Java does not use the traditional cursor but instead are more tight and safer reference. Subjects in Java, except for primitive types, are accessed through reference. This allows building complex data structures safely in a data type without risks related to the cursor in C/C ++.
Java is designed to handle errors in a smart and effective way, thanks to the strong exception management mechanism. In Java, errors are not only captured and processed in a specific place in the program through the "Catch" code block, but also packed into exceptions. Each of these objects brings information about the cause of the error, making it easy for programmers to understand and handle errors correctly. The Java translation requires the method to declare the exceptions that it may arise, or to handle them immediately. This helps to bring the error information to the same level with other information such as the return data type or the method of the method. Thereby, when programming, you can predict and prepare for possible situations, ensuring that your application will operate more stable and safer.
In software programming and development, the Naming Convention is a collection of rules for selecting names of variables, jaws, classes, and other objects in the source code. The identification convention makes the source code easier to read, easy to understand and easier to maintain. My storage strictly complies with this convention, mentioned below.
Class: The class name always starts with the letter printed (pascalcase). If the class name consists of many words, each word must also start with floral print. For example: Student , Car , ColorChooser .
Interface: Like the class, the name of the interface also uses Pascalcase. Often the interface name will start with capital letters such as I or use the dumb/suffix like able or ible to describe the feature, such as Runnable , Accessible .
The method of the method always starts in normal letters and follows Camelcase. The method name is usually the verbs or verb phrases describing the action that the method performs. For example: getName() , calculateTotalWidth() .
The variable name should also start with normal letters and followed by camelcase. The variable name should be clear and describe the value that they represent. For example: height , numberOfStudents .
An example of the Dog class:
package com . example . animals ;
/**
* A generic Dog class that can be used as a base class for specific breeds.
*/
public class Dog {
private String name ;
private int age ;
/**
* Constructor for Dog class.
*
* @param name The name of the dog.
* @param age The age of the dog.
*/
public Dog ( String name , int age ) {
this . name = name ;
this . age = age ;
}
/**
* Returns the name of the dog.
*
* @return The name of the dog.
*/
public String getName () {
return name ;
}
/**
* Sets the name of the dog.
*
* @param name New name for the dog.
*/
public void setName ( String name ) {
this . name = name ;
}
/**
* Returns the age of the dog.
*
* @return The age of the dog.
*/
public int getAge () {
return age ;
}
/**
* Sets the age of the dog.
*
* @param age New age for the dog.
*/
public void setAge ( int age ) {
this . age = age ;
}
/**
* Provides a string representation of the dog.
*
* @return A string describing the dog's details.
*/
@ Override
public String toString () {
return "Dog[name=" + name + ", age=" + age + "]" ;
}
}| Access indications | public | Protected | default | Private | |
|---|---|---|---|---|---|
| Along with package | Inside the class | Have | Have | Have | Have |
| Sub -class | Have | Have | Have | Are not | |
| Other class | Have | Have | Have | Are not | |
| Different package | Sub -class | Have | Have | Are not | Are not |
| Other class | Have | Are not | Are not | Are not | |
Unified Modeling Language (UML) is a standard graphic modeling tool, designed to sketch, describe and documents about different aspects of the application software. It is especially useful in the field of object -oriented programming, because it provides an intuitive way to show classes, objects, and relationships between them. UML includes many different types of diagrams, but in the context of object -oriented programming, class diagram (class diagrams) and interactive diagram (interaction diagrams) are the two most commonly used types.
UML allows programmers to describe the structure of the system using class diagrams. This diagram shows classes in the system, attributes, their methods, and most importantly, the relationship between classes such as inheritance, linkage, synthesis and combination. This helps programmers understand and design system more systematically.
Once the UML diagram has been completed, it can be used as the basis for writing source code. In OOP, the transfer from the layer diagram to the source code (usually Java, C#, or C ++) is quite direct, due to the similarity between the concepts described in UML and the layer structure in these programming languages.
UML helps to clearly define the relationships between objects, highlight the way of communication and interaction between them through the sequence diagram (sequence diagrams) and collaboration diagram (collaboration diagrams). This helps programmers understand the data flow and control in the application.
Before starting to write codes, UML helps the development group can detect and correct design problems. The unity in the use of UML also helps members in the group easily understand each other's ideas, thereby increasing the efficiency of working coordination.
UML provides full documents for the software, which is very useful in the maintenance and software upgrade stage. A good UML diagram can help new people participating in the project quickly capture the structure and function of the system.
Class diagram (class diagram) is one of the types of diagrams used in UML and it plays an important role in modeling the software system. Class Diagram provides an overview of the structure of an application by displaying the system layers, their attributes and methods, and the relationship between those layers. These relationships may include: link (association), inheritance (Inheritance), enforcement (realization), dependency, Aggrease, composition.
A class represents a concept that includes status (attribute) and behavior (method). Each attribute has one type. Each method has a signature. The class name is the only compulsory information.
Consider the following example:

This UML diagram corresponds to Class Animal in the code as follows:
public class Animal {
// Các thuộc tính của lớp
public String name ; // Biến thành viên công khai cho tên
private int age ; // Biến thành viên riêng tư cho tuổi
private String species ; // Biến thành viên riêng tư cho loài
// Phương thức getter cho thuộc tính name
public String getName () {
return name ;
}
// Phương thức setter cho thuộc tính name
public void setName ( String name ) {
this . name = name ;
}
} Symbols + , - and # and # and # and method names in a layer indicate the level of access capacity of the attribute and the method. Specifically:
+ indicates the attribute or method of public (public).- indicating the properties or privacy methods (private).# biểu thị thuộc tính hoặc phương thức bảo vệ (protected).
Flyable có phương thức fly() , lớp Bird có thể thực thi interface này bằng cách triển khai phương thức fly() .School có thể có nhiều đối tượng của lớp Teacher , nhưng các giáo viên vẫn tồn tại độc lập với trường học.House có thể chứa nhiều đối tượng của lớp Room . Khi đối tượng House bị hủy, các Room cũng sẽ bị hủy theo.| Kế thừa | Kết tập | |
|---|---|---|
| Define | - Kế thừa là một cơ chế trong đó một lớp (gọi là lớp con) có thể kế thừa tính chất và phương thức của một lớp khác (gọi là lớp cha). - Cho phép lớp con tái sử dụng mã lệnh của lớp cha mà không cần phải viết lại. - Tương ứng với mối quan hệ "is-a". | - Kết tập là một dạng của quan hệ "có" giữa hai lớp. - Biểu thị một mối quan hệ trong đó một đối tượng có thể chứa hoặc tham chiếu đến đối tượng khác, nhưng hai đối tượng có thể tồn tại độc lập với nhau. - Tương ứng với mối quan hệ "has-a". |
| Purpose | - Tái sử dụng mã lệnh và cải thiện tính mô-đun hóa của ứng dụng. - Cũng hỗ trợ tính đa hình, cho phép phương thức của lớp con có thể ghi đè hoặc mở rộng phương thức của lớp cha. - Ví dụ: Lớp Animal có phương thức move(), lớp Bird và Fish có thể kế thừa lớp Animal và sử dụng hoặc ghi đè phương thức move() để phù hợp với bản chất di chuyển của chúng. | - Biểu diễn mối quan hệ giữa các đối tượng, nơi các đối tượng có thể có mối quan hệ một phần với nhau nhưng không phụ thuộc hoàn toàn vào nhau. - Giúp tăng cường sự linh hoạt trong cấu trúc dữ liệu và quản lý các đối tượng phức tạp. - Ví dụ, lớp Square có thể có các đối tượng của lớp Point. Mỗi hình vuông bao gồm bốn đối tượng của lớp điểm (chỉ các đỉnh) nhưng các điểm có thể tồn tại độc lập mà không là đỉnh của hình vuông. |
| Sự phụ thuộc | - Lớp con phụ thuộc mạnh mẽ vào lớp cha vì nó sử dụng trực tiếp các tính chất và phương thức của lớp cha. | - Các đối tượng liên quan có thể tồn tại độc lập; chúng không phụ thuộc mạnh mẽ vào nhau. |
| Ability | - Mở rộng hoặc tùy chỉnh lớp cha. - Mô hình hóa mối quan hệ phân cấp. | - Quản lý các đối tượng có liên kết. - Mô hình hóa mối quan hệ thực thể. |
Xét ví dụ sau đây:

Triển khai sơ đồ UML này trong Java như sau:
public class Person {
private String name ;
private int age ;
private Address address ; // Liên kết sử dụng lớp Address
public Person ( String name , int age , Address address ) {
this . name = name ;
this . age = age ;
this . address = address ;
}
// Getter và Setter cho các thuộc tính
public String getName () {
return name ;
}
public void setName ( String name ) {
this . name = name ;
}
public int getAge () {
return age ;
}
public void setAge ( int age ) {
this . age = age ;
}
public Address getAddress () {
return address ;
}
public void setAddress ( Address address ) {
this . address = address ;
}
}
// Định nghĩa lớp Student kế thừa từ Person
public class Student extends Person {
public Student ( String name , int age , Address address ) {
super ( name , age , address );
}
}
// Định nghĩa lớp Teacher kế thừa từ Person
public class Teacher extends Person {
public Teacher ( String name , int age , Address address ) {
super ( name , age , address );
}
}
// Định nghĩa lớp Staff kế thừa từ Person
public class Staff extends Person {
public Staff ( String name , int age , Address address ) {
super ( name , age , address );
}
}
// Định nghĩa lớp Address
public class Address {
private String street ;
private String city ;
private String country ;
public Address ( String street , String city , String country ) {
this . street = street ;
this . city = city ;
this . country = country ;
}
// Getter và Setter cho các thuộc tính
public String getStreet () {
return street ;
}
public void setStreet ( String street ) {
this . street = street ;
}
public String getCity () {
return city ;
}
public void setCity ( String city ) {
this . city = city ;
}
public String getCountry () {
return country ;
}
public void setCountry ( String country ) {
this . country = country ;
}
}
// Định nghĩa lớp Department chứa Teacher và Course
public class Department {
private String name ;
private List < Teacher > teachers ; // Aggregation
private List < Course > courses ; // Composition
public Department ( String name ) {
this . name = name ;
this . teachers = new ArrayList <>();
this . courses = new ArrayList <>();
}
// Phương thức thêm giáo viên và khóa học
public void addTeacher ( Teacher teacher ) {
teachers . add ( teacher );
}
public void addCourse ( Course course ) {
courses . add ( course );
}
}
// Định nghĩa lớp Course
public class Course {
private String courseName ;
private List < Teacher > teachers ; // Association
public Course ( String courseName ) {
this . courseName = courseName ;
this . teachers = new ArrayList <>();
}
public void addTeacher ( Teacher teacher ) {
teachers . add ( teacher );
}
}
// Định nghĩa interface Maintainable
public interface Maintainable {
void maintain ();
}
// Định nghĩa lớp School
public class School implements Maintainable {
private String name ;
private List < Department > departments ; // Composition
public School ( String name ) {
this . name = name ;
this . departments = new ArrayList <>();
}
public void addDepartment ( Department department ) {
departments . add ( department );
}
// Triển khai phương thức từ interface Maintainable
@ Override
public void maintain () {
System . out . println ( "Maintaining the school facilities..." );
// Logic bảo trì cơ sở vật chất có thể được thực hiện ở đây
}
}