Mẫu hàm khởi tạo
Thuộc phần Lập trình hướng đối tượng trong hành trình C của Coddy. Bài học 12 trên 61.
Trong các ngôn ngữ như Java hoặc C++, bạn tạo đối tượng bằng hàm khởi tạo: những hàm đặc biệt tự động cấp phát bộ nhớ và khởi tạo các trường. C không có tính năng này, nhưng mình có thể mô phỏng bằng một quy tắc đơn giản: hàm create_.
Hàm khởi tạo trong C thường thực hiện ba việc: cấp phát bộ nhớ bằng malloc, khởi tạo tất cả các trường với giá trị phù hợp và trả về con trỏ đến đối tượng mới:
typedef struct {
char *name;
int age;
} Person;
Person *create_person(const char *name, int age) {
Person *p = malloc(sizeof(Person));
p->name = malloc(strlen(name) + 1);
strcpy(p->name, name);
p->age = age;
return p;
}
Hàm trả về một con trỏ vì đối tượng nằm trên heap, không phải stack. Điều này có nghĩa là đối tượng vẫn tồn tại sau khi hàm trả về và bạn có thể tự do truyền nó đi nơi khác. Bên gọi sử dụng con trỏ như sau:
Person *alice = create_person("Alice", 30);
printf("%s is %d years old\n", alice->name, alice->age);
Hãy chú ý cách hàm khởi tạo xử lý mọi chi tiết phức tạp: cấp phát cấu trúc, cấp phát không gian cho chuỗi và sao chép dữ liệu. Bên gọi chỉ cần cung cấp các giá trị ban đầu rồi nhận về một đối tượng có thể dùng ngay. Cách này gói gọn logic tạo đối tượng tại một nơi, giúp code của bạn gọn gàng hơn và ít lỗi hơn.
Thử thách
DễHãy tạo một module Book sử dụng mẫu hàm khởi tạo để tạo các đối tượng sách trên heap. Bạn sẽ luyện viết một hàm create_ xử lý toàn bộ việc cấp phát và khởi tạo bộ nhớ, rồi trả về một con trỏ sẵn sàng sử dụng.
Bạn sẽ tạo ba tệp:
book.h: Khai báo một cấu trúcBookcó hai thành viên:char *title(con trỏ đến một chuỗi được cấp phát động) vàint pages. Đồng thời khai báo hàm khởi tạocreate_book, nhận một chuỗi tiêu đề và số trang, sau đó trả về con trỏ đến mộtBookmới được tạo. Dùng include guard với ký hiệuBOOK_H.book.c: Triển khai hàmcreate_book. Hàm khởi tạo cần cấp phát bộ nhớ cho chính cấu trúcBook, sau đó cấp phát vùng nhớ riêng cho chuỗi tiêu đề (nhớ tính cả ký tự kết thúc chuỗi), sao chép tiêu đề vào vùng nhớ mới, đặt trường số trang rồi trả về con trỏ đếnBookmới.main.c: Dùng hàm khởi tạo để tạo một quyển sách và hiển thị thông tin.
Bạn sẽ nhận hai đầu vào: tiêu đề sách (một chuỗi) và số trang (một số nguyên).
Trong tệp main, dùng create_book để tạo một quyển sách mới với các giá trị đã cho, sau đó in thông tin theo định dạng sau:
Title: {title}
Pages: {pages}Ví dụ, với đầu vào The C Programming Language và 272, đầu ra sẽ là:
Title: The C Programming Language
Pages: 272Hãy nhớ rằng hàm khởi tạo đóng gói toàn bộ logic tạo đối tượng: bên gọi chỉ cần cung cấp các giá trị ban đầu và nhận về một đối tượng đã được khởi tạo đầy đủ, sẵn sàng sử dụng.
Tự làm thử
#include <stdio.h>
#include <stdlib.h>
#include "book.h"
int main() {
char title[256];
int pages;
// Đọc đầu vào
fgets(title, sizeof(title), stdin);
// Xóa ký tự xuống dòng nếu có
for (int i = 0; title[i]; i++) {
if (title[i] == '\n') {
title[i] = '\0';
break;
}
}
scanf("%d", &pages);
// TODO: Dùng create_book để tạo cuốn sách mới với các giá trị đã cho
// TODO: In thông tin sách theo định dạng yêu cầu:
// Tiêu đề: {title}
// Số trang: {pages}
// TODO: Đừng quên giải phóng bộ nhớ đã cấp phát khi xong
return 0;
}
Bài học này có một bài trắc nghiệm ngắn. Bắt đầu bài học để trả lời và theo dõi tiến độ.
Tất cả bài học trong Lập trình hướng đối tượng
1Kiến thức cơ bản về lập trình mô-đun
Tệp tiêu đềInclude guardTệp mã nguồnHàm staticÔn tập: Máy tính mô-đun4Tính đóng gói
Khái niệm con trỏ mờĐịnh nghĩa struct mờHàm truy xuất và hàm gánKiểm tra tính hợp lệ trong hàm gánÔn tập: Hộp bí mật2Đối tượng và phương thức
Struct dưới dạng đối tượngCon trỏ 'Self'Tính đúng đắn của constCon trỏ và giá trịPhương thức hỗ trợÔn tập: trình quản lý Point5Dự án: Tài khoản ngân hàng đơn giản
Thiết lập dự ánTriển khai tài khoản3Vòng đời đối tượng
Mẫu hàm khởi tạoMẫu hàm hủyKhởi tạo trên ngăn xếpSao chép sâuÔn tập: lớp bao bọc chuỗi6Kế thừa bằng cách kết hợp
Nhúng structQuy tắc thành viên đầu tiênTruy cập thành viên lớp chaUpcastingÔn tập: hệ phân cấp hình dạngTự luyện tập: Trình biên dịch C online