








Preview text:
Bài tập lập trình hướng đối tượng
1. Lập trình hướng đối tượng (OOP):
Tóm tắt: Lập trình hướng đối tượng (OOP) là một phương pháp
lập trình mà mọi thực thể trong chương trình được coi như các
đối tượng có thể tương tác với nhau thông qua việc trao đổi
thông điệp. OOP tập trung vào việc tổ chức mã nguồn thành các
đối tượng độc lập, mỗi đối tượng có các thuộc tính và hành vi riêng biệt. VD: #include #include
// Định nghĩa struct Student typedef struct {
char name[50]; // Tên của học sinh int age;
// Tuổi của học sinh
float score; // Điểm số của học sinh } Student;
// Phương thức hiển thị thông tin của Student
void display_info(Student student) {
printf("Name: %s\n", student.name);
printf("Age: %d\n", student.age);
printf("Score: %.2f\n", student.score); } int main() {
// Tạo đối tượng 'john' từ lớp Student và khởi tạo thông tin Student john; strcpy(john.name, "John"); john.age = 20; john.score = 85.5;
// Hiển thị thông tin của 'john'
printf("Information of John:\n"); display_info(john);
// Tạo đối tượng 'alice' từ lớp Student và khởi tạo thông tin Student alice; strcpy(alice.name, "Alice"); alice.age = 19; alice.score = 90.0;
// Hiển thị thông tin của 'alice'
printf("\nInformation of Alice:\n"); display_info(alice); return 0; } Trong mã nguồn này:
Chúng ta định nghĩa một cấu trúc (struct) tên là Student để lưu
trữ thông tin của học sinh với các thuộc tính như tên, tuổi và điểm số.
Hàm display_info() được triển khai để hiển thị thông tin của một đối tượng Student.
Trong hàm main(), chúng ta tạo các đối tượng john và alice từ
lớp Student và khởi tạo thông tin cho mỗi đối tượng, sau đó
hiển thị thông tin của từng học sinh.
2. Lớp và đối tượng (class & object):
Tóm tắt: Lớp (class) là một mô hình hoặc khuôn mẫu để tạo ra
các đối tượng. Mỗi lớp định nghĩa các thuộc tính và phương
thức mà các đối tượng tạo ra từ lớp đó sẽ thừa kế. Đối tượng
(object) là một phiên bản cụ thể của một lớp, có thể thực hiện
các hành động và lưu trữ dữ liệu. VD: #include
// Định nghĩa struct Car typedef struct {
char brand[20]; // Hãng xe
char model[20]; // Dòng xe
char color[20]; // Màu sắc int speed; // Tốc độ (mph) } Car;
// Phương thức tăng tốc độ của xe
void accelerate(Car *car, int increment) {
car->speed += increment;
printf("Accelerating. Current speed: %d mph\n", car->speed); }
// Phương thức giảm tốc độ của xe
void brake(Car *car, int decrement) {
car->speed -= decrement;
printf("Braking. Current speed: %d mph\n", car->speed); } int main() {
// Tạo đối tượng 'toyota_camry' từ struct 'Car' và khởi tạo thông tin
Car toyota_camry = {"Toyota", "Camry", "Black", 60};
// In thông tin về 'toyota_camry'
printf("Car: %s %s\n", toyota_camry.brand, toyota_camry.model);
printf("Color: %s\n", toyota_camry.color);
printf("Speed: %d mph\n", toyota_camry.speed);
// Tăng tốc độ của 'toyota_camry' lên 80 mph
accelerate(&toyota_camry, 20); return 0; } Trong mã nguồn này:
Chúng ta định nghĩa một cấu trúc (struct) tên là Car để đại diện cho đối tượng xe.
Các phương thức accelerate() và brake() được triển khai để thay đổi tốc độ của xe.
Trong hàm main(), chúng ta tạo một đối tượng toyota_camry từ
struct Car và gọi các phương thức tương ứng để tăng tốc độ của nó. 3. Kế thừa (Inheritance):
Tóm tắt: Kế thừa là một khái niệm trong OOP cho phép một lớp
mới (lớp con) kế thừa các thuộc tính và phương thức của một lớp
hiện có (lớp cha). Lớp con có thể mở rộng hoặc sửa đổi các tính
năng của lớp cha và cũng có thể thêm các tính năng mới. VD: #include #include
// Định nghĩa struct Animal typedef struct {
char name[20]; // Tên của động vật int age;
// Tuổi của động vật } Animal;
// Phương thức kêu của Animal
void makeSound(Animal *animal) {
printf("%s makes a sound.\n", animal->name); }
// Định nghĩa struct Dog, kế thừa từ Animal typedef struct {
Animal baseAnimal; // Kế thừa từ lớp Animal } Dog;
// Phương thức kêu của Dog void bark(Dog *dog) {
printf("%s barks.\n", dog->baseAnimal.name); }
// Định nghĩa struct Cat, kế thừa từ Animal typedef struct {
Animal baseAnimal; // Kế thừa từ lớp Animal } Cat;
// Phương thức kêu của Cat void meow(Cat *cat) {
printf("%s meows.\n", cat->baseAnimal.name); } int main() {
// Tạo đối tượng 'dog' từ lớp Dog và khởi tạo thông tin Dog dog;
strcpy(dog.baseAnimal.name, "Buddy");
dog.baseAnimal.age = 5;
// Gọi phương thức kêu của Dog
makeSound(&dog.baseAnimal); // makeSound() được sử dụng từ Animal bark(&dog);
// Tạo đối tượng 'cat' từ lớp Cat và khởi tạo thông tin Cat cat;
strcpy(cat.baseAnimal.name, "Whiskers");
cat.baseAnimal.age = 3;
// Gọi phương thức kêu của Cat
makeSound(&cat.baseAnimal); // makeSound() được sử dụng từ Animal meow(&cat); return 0; } Trong mã nguồn này:
Chúng ta định nghĩa một cấu trúc (struct) tên là Animal để đại diện
cho động vật với các thuộc tính chung như tên và tuổi.
Các phương thức makeSound(), bark(), và meow() được triển khai
để mô tả hành vi của các loài động vật khác nhau.
Lớp Dog và Cat được định nghĩa là các struct riêng biệt, nhưng
chúng kế thừa từ Animal, tức là chúng có tất cả các thuộc tính của Animal.
Trong hàm main(), chúng ta tạo các đối tượng dog và cat từ các lớp
con Dog và Cat và gọi các phương thức tương ứng của chúng. 4. Đa hình (Polymorphism):
Tóm tắt: Đa hình cho phép một đối tượng có thể hiểu và phản ứng
với các phương thức khác nhau theo cách riêng của nó. Điều này
cho phép chúng ta sử dụng cùng một phương thức với các đối
tượng khác nhau mà không cần biết cụ thể loại đối tượng đó là gì. VD: #include
// Định nghĩa struct Shape typedef struct {
// Không có thuộc tính cụ thể cho Shape vì mỗi lớp con sẽ tự xác định thuộc tính của nó } Shape;
// Phương thức tính diện tích của Shape (được cài đặt như một hàm ảo)
float calculate_area(Shape *shape) {
// Hàm ảo, sẽ được ghi đè bởi các lớp con return 0; }
// Định nghĩa struct Circle, kế thừa từ Shape typedef struct {
Shape baseShape; // Kế thừa từ lớp Shape float radius;
// Bán kính của hình tròn } Circle;
// Ghi đè phương thức tính diện tích cho Circle
float calculate_area(Shape *shape) {
Circle *circle = (Circle *)shape; // Ép kiểu từ Shape sang Circle
return 3.14 * circle->radius * circle->radius; // Diện tích của hình tròn }
// Định nghĩa struct Rectangle, kế thừa từ Shape typedef struct {
Shape baseShape; // Kế thừa từ lớp Shape float length;
// Chiều dài của hình chữ nhật float width;
// Chiều rộng của hình chữ nhật } Rectangle;
// Ghi đè phương thức tính diện tích cho Rectangle
float calculate_area(Shape *shape) {
Rectangle *rectangle = (Rectangle *)shape; // Ép kiểu từ Shape sang Rectangle
return rectangle->length * rectangle->width; // Diện tích của hình chữ nhật } int main() {
// Tạo đối tượng 'circle' từ lớp Circle và khởi tạo thông tin
Circle circle = {{}, 5}; // Bán kính là 5
// Tính và in diện tích của hình tròn
printf("Area of circle: %.2f\n", calculate_area((Shape *)&circle));
// Tạo đối tượng 'rectangle' từ lớp Rectangle và khởi tạo thông tin
Rectangle rectangle = {{}, 4, 6}; // Chiều dài là 4, chiều rộng là 6
// Tính và in diện tích của hình chữ nhật
printf("Area of rectangle: %.2f\n", calculate_area((Shape *)&rectangle)); return 0; }
Trong mã nguồn này:
Chúng ta định nghĩa một cấu trúc (struct) tên là Shape để đại diện
cho hình dạng với một phương thức ảo calculate_area().
Lớp con Circle và Rectangle kế thừa từ Shape và ghi đè phương
thức calculate_area() để tính diện tích của hình tròn và hình chữ nhật tương ứng.
Trong hàm main(), chúng ta tạo các đối tượng circle và rectangle từ
các lớp con và gọi phương thức calculate_area() để tính và in ra diện tích của chúng.
Document Outline
- 1. Lập trình hướng đối tượng (OOP):
- VD:
- Trong mã nguồn này:
- 2. Lớp và đối tượng (class & object):
- VD:
- Trong mã nguồn này:
- 3. Kế thừa (Inheritance):
- VD: (1)
- Trong mã nguồn này:
- 4. Đa hình (Polymorphism):
- VD: (2)
- Trong mã nguồn này: