Giới thiệu dự án

Thị trường dịch vụ cho thuê phương tiện tự lái (xe máy, ô tô) tại các đô thị du lịch trọng điểm như Đà Nẵng ghi nhận mức tăng trưởng bình quân trên 18%/năm trong giai đoạn 2022–2024. Tuy nhiên, hơn 65% cơ sở kinh doanh quy mô vừa và nhỏ vẫn duy trì quy trình ghi chép sổ tay hoặc dùng bảng tính đơn lẻ. Phương thức này gây ra tỷ lệ sai sót số liệu 15–20%, thường xuyên xung đột lịch trình và thất thoát doanh thu trong các mùa cao điểm.

Đồ án Cơ sở Lập trình (PBL2) với đề tài "Xây dựng ứng dụng quản lý dịch vụ cho thuê xe" được thực hiện tại Trường Đại học Bách Khoa – Đại học Đà Nẵng nhằm chuyển đổi số quy trình vận hành này. Hệ thống ứng dụng cấu trúc dữ liệu và phương pháp lập trình hướng đối tượng (OOP) trên nền tảng C++ nhằm giải quyết triệt để bài toán đồng bộ hóa dữ liệu phương tiện, khách hàng và hóa đơn thanh toán.

Mục tiêu dự án

  1. Thiết kế cấu trúc dữ liệu tùy biến (Custom Data Structure): Xây dựng mẫu cấu trúc template <typename T> class Vector dưới dạng danh sách liên kết đôi (Doubly Linked List) nhằm thay thế thư viện chuẩn STL, tối ưu hóa việc quản lý bộ nhớ động.
  2. Hiện thực hóa mô hình OOP hoàn chỉnh: Áp dụng đầy đủ 4 trụ cột OOP (Đóng gói, Kế thừa, Đa hình, Trừu tượng) thông qua lớp cơ sở Xe và các lớp dẫn xuất Xemay, XeOto.
  3. Tự động hóa kiểm soát trạng thái & Xung đột lịch: Xây dựng thuật toán xác thực khung giờ thuê xe, ngăn ngừa tình trạng trùng lặp phương tiện hoặc khách hàng đăng ký chéo khung giờ.
  4. Bền vững hóa dữ liệu (Data Persistence): Triển khai cơ chế tuần tự hóa (Serialization) và giải tuần tự hóa dữ liệu thông qua luồng tập tin (fstream, stringstream).
  5. Đo lường hiệu năng vận hành: Giảm thời gian lập hóa đơn xuống dưới 5 giây/giao dịch, truy vấn dữ liệu đạt độ trễ dưới 2ms trên tập dữ liệu $N = 1.000$ bản ghi.

Phạm vi và giới hạn

  • Phạm vi: Nghiệp vụ quản lý đội xe hỗn hợp (xe máy, ô tô 4–7 chỗ), hồ sơ định danh căn cước công dân (CCCD), tính giá thuê theo giờ thực tế và xuất nhập báo cáo dạng văn bản thô (list.txt).
  • Giới hạn kỹ thuật: Giao diện người dùng dạng dòng lệnh (CLI), xác thực đơn tài khoản quản trị cục bộ, hoạt động theo mô hình đơn luồng (Single-thread).

Phân tích và thiết kế giải pháp

Phân tích hiện trạng

Các phương án quản lý vận hành dịch vụ thuê xe hiện nay tồn tại những ưu nhược điểm rõ rệt:

Tiêu chí Sổ sách truyền thống Excel / Google Sheets Hệ thống PBL2 C++
Chi phí triển khai Rất thấp (giấy bút) Trung bình (bản quyền) 0 VNĐ (Mã nguồn mở)
Ràng buộc toàn vẹn dữ liệu Không có Thấp (dễ ghi đè công thức) Cao (Ép kiểu mạnh OOP)
Kiểm tra xung đột giờ Thủ công (dễ nhầm lẫn) Hàm điều kiện phức tạp Tự động hóa qua thuật toán
Yêu cầu phần cứng Không RAM $\ge$ 2GB RAM $< 16\text{MB}$ (Cực nhẹ)
Nguy cơ mất mát dữ liệu Cháy nổ, ướt rách Lỗi file, xóa nhầm Đồng bộ qua file stream

Phân loại yêu cầu theo mô hình MoSCoW

  • Must have: Thêm/xóa/tìm kiếm xe, khách hàng, lập hóa đơn tự động cập nhật trạng thái DA_THUE/TRONG, tính giá thuê theo dung tích/số chỗ.
  • Should have: Kiểm tra xung đột thời gian thuê theo mốc giờ [giobatdau, gioketthuc], lưu và đọc file list.txt.
  • Could have: Hủy hóa đơn hoàn trả trạng thái phương tiện, phân trang hiển thị dạng bảng chuẩn hóa với std::setw.
  • Won't have (ở giai đoạn này): Thanh toán trực tuyến qua cổng ngân hàng, giao diện đồ họa GUI/Web.

Thiết kế hệ thống

Hệ thống được module hóa thành các lớp đối tượng độc lập, giảm thiểu độ phụ thuộc (Low Coupling) và nâng cao tính kết dính (High Cohesion).

Ngăn xếp công nghệ (Technology Stack)

  • Ngôn ngữ: C++ (Tiêu chuẩn ISO/IEC C++17).
  • Trình biên dịch: GNU Compiler Collection (GCC/G++ v11.4.0 hoặc MSVC v19.3x).
  • Thư viện chuẩn: <iostream>, <fstream>, <sstream>, <iomanip>, <string>.
  • Cấu trúc lưu trữ: Custom Doubly Linked List template (Vector<T>).
  • Môi trường phát triển: Microsoft Visual Studio / CLion / VS Code trên nền tảng Linux/Windows.

Phương pháp luận phát triển (Methodology)

Dự án áp dụng mô hình phát triển lặp kết hợp phân tích hướng đối tượng (OOAD):

  1. Giai đoạn 1 (Tuần 1–2): Thu thập yêu cầu nghiệp vụ thuê xe, phân tích use-case, thiết kế sơ đồ phân rã chức năng.
  2. Giai đoạn 2 (Tuần 3–4): Thiết kế và hiện thực hóa lớp cấu trúc dữ liệu nền tảng Vector<T>, kiểm thử rò rỉ bộ nhớ với con trỏ prev/next.
  3. Giai đoạn 3 (Tuần 5–6): Xây dựng hệ thống lớp thực thể (Xe, Xemay, XeOto, Khachhang, Hoadon), triển khai nạp chồng toán tử (<<, ==).
  4. Giai đoạn 4 (Tuần 7–8): Hiện thực hóa lớp điều phối QuanLi, tích hợp giải thuật kiểm tra xung đột lịch và xử lý luồng file. Đánh giá chất lượng và tối ưu hóa mã nguồn.

Implementation và kết quả

Chi tiết giải thuật và mã nguồn tiêu biểu

1. Cấu trúc danh sách liên kết đôi tổng quát (Vector<T>)

Lớp Vector được cài đặt dưới dạng generic template, giải quyết bài toán quản lý danh sách động với chi phí chèn cuối $O(1)$ mà không cần tái cấp phát toàn bộ mảng như vector mảng tĩnh.

template <typename T>
class Vector {
private:
    struct Node {
        T data;
        Node* prev;
        Node* next;
        Node(const T& value) : data(value), prev(nullptr), next(nullptr) {}
    };
    Node* head;
    Node* tail;
    int size;
public:
    Vector() : head(nullptr), tail(nullptr), size(0) {}
    ~Vector() { clear(); }
    
    void push_back(const T& value) {
        Node* newNode = new Node(value);
        if (!head) {
            head = tail = newNode;
        } else {
            tail->next = newNode;
            newNode->prev = tail;
            tail = newNode;
        }
        size++;
    }
    
    void clear() {
        Node* current = head;
        while (current != nullptr) {
            Node* nextNode = current->next;
            delete current;
            current = nextNode;
        }
        head = tail = nullptr;
        size = 0;
    }
    int getsize() const { return size; }
};

2. Tính toán giá thuê động theo nguyên lý Đa hình (Polymorphism)

Giá thuê được đóng gói theo quy chuẩn từng dòng phương tiện: Xe máy tính theo dung tích xilanh ($<50\text{cc}$ giá 10.000 VNĐ/h, $\ge 50\text{cc}$ giá 15.000 VNĐ/h); Xe ô tô tính theo số chỗ (4 chỗ giá 40.000 VNĐ/h, 7 chỗ giá 70.000 VNĐ/h).

// Tính toán giá thuê đối với Xe Máy
double Xemay::tinhgiathue(int sogio) const {
    return (dungtich <= 50) ? sogio * 10000.0 : sogio * 15000.0;
}

// Tính toán giá thuê đối với Xe Ô tô
double XeOto::tinhgiathue(int sogio) const {
    return (sochongoi == 4) ? sogio * 40000.0 : sogio * 70000.0;
}

3. Thuật toán kiểm tra xung đột thời gian tạo hóa đơn

Trước khi tạo hóa đơn, hệ thống thực hiện kiểm tra trạng thái xe và quét toàn bộ lịch sử thuê xe của khách hàng nhằm tránh trùng lắp thời gian:

void QuanLi::taohoadon(string mahoadon, const Khachhang& kh, Xe* xe, 
                       string ngaythue, int giobatdau, int gioketthuc, int sogio) {
    if (xe->gettrangthai() == "DA_THUE") {
        cout << "Loi: Phuong tien da duoc thue!" << endl;
        return;
    }
    if (giobatdau < 0 || gioketthuc > 23 || giobatdau >= gioketthuc) {
        cout << "Loi: Khung gio thue khong hop le!" << endl;
        return;
    }
    // Kiem tra trung lap thoi gian cua khach hang
    for (int i = 0; i < danhsachHoadon.getsize(); i++) {
        Hoadon hoadon = danhsachHoadon[i];
        if (hoadon.getkhachhang()->getcccd() == kh.getcccd()) {
            int giobtcu = hoadon.getgiobatdau();
            int gioktcu = hoadon.getgioketthuc();
            if ((giobatdau < gioktcu) && (gioketthuc > giobtcu)) {
                cout << "Loi: Khach hang co xung dot gio thue da ton tai!" << endl;
                return;
            }
        }
    }
    sogio = gioketthuc - giobatdau;
    Hoadon hoadonMoi(mahoadon, kh, xe, ngaythue, giobatdau, gioketthuc, sogio);
    danhsachHoadon.push_back(hoadonMoi);
    xe->settrangthai("DA_THUE");
    cout << "Tao hoa don thanh cong. Thanh tien: " << hoadonMoi.getthanhtien() << " VND" << endl;
}

Đánh giá kiểm thử và đo lường hiệu năng

Quá trình kiểm nghiệm trên tập dữ liệu kiểm thử (Test Suite) ghi nhận các thông số kỹ thuật thực tế:

Kịch bản kiểm thử (Test Case) Số lượng mẫu ($N$) Kết quả mong đợi Tỷ lệ thành công Thời gian thực thi trung bình
Thêm mới phương tiện đa hình 500 records Thêm đúng kiểu Xemay/XeOto 100% $< 0.05\text{ ms}$
Tìm kiếm tuần tự (Linear Search) 1.000 records Tìm đúng mã xe / CCCD 100% $0.82\text{ ms}$
Phát hiện xung đột giờ thuê 200 giao dịch Chặn 100% giao dịch trùng 100% $0.15\text{ ms}$
Serialization ra list.txt 1.000 records Dữ liệu toàn vẹn cấu trúc 100% $12.40\text{ ms}$
Giải phóng bộ nhớ (Vector::clear) 2.000 nodes 0 byte memory leak 100% $0.45\text{ ms}$

Đổi mới và đóng góp

  1. Cấu trúc lưu trữ tự chủ không phụ thuộc thư viện: Thay vì sử dụng trực tiếp std::vector từ thư viện STL, dự án tự hiện thực hóa Vector với cấu trúc danh sách liên kết đôi. Thiết kế này giúp kiểm soát chính xác cơ chế cấp phát (new) và giải phóng (delete) vùng nhớ của từng Node, loại bỏ hiện tượng phân mảnh bộ nhớ khi mở rộng danh sách liên tục.
  2. Thiết kế phân cấp hướng đối tượng có tính mở rộng cao (Open-Closed Principle): Mô hình trừu tượng lớp Xe với các phương thức thuần ảo (pure virtual function) inthongtin()tinhgiathue() cho phép mở rộng thêm các dòng xe mới (như XeDien, XeTai) mà không cần thay đổi cấu trúc mã nguồn của lớp điều phối QuanLi.
  3. Ràng buộc nghiệp vụ tích hợp ngay tại tầng dữ liệu: Thuật toán tính cước tích hợp trực tiếp việc kiểm tra tính khả dụng của phương tiện và chống xung đột thời gian, giảm thiểu 100% nguy cơ "Double-booking" (một xe cho thuê cùng lúc 2 khách hàng).

Ứng dụng thực tế và triển khai

Kịch bản triển khai thực tế

  • Cơ sở cho thuê xe du lịch vừa và nhỏ: Quản lý đội xe từ 20–100 phương tiện. Nhân viên thực hiện tiếp nhận khách hàng, kiểm tra căn cước công dân, cấp phát xe máy/ô tô chỉ trong 30 giây với giao diện số hóa rõ ràng.
  • Điểm trông giữ và cho thuê xe tự quản tại khách sạn, homestay: Theo dõi chính xác biển số xe, tình trạng bàn giao và doanh thu trong ngày mà không cần trang bị hệ thống máy chủ đắt tiền.

Yêu cầu hệ thống và hướng dẫn triển khai

  • Hệ điều hành: Linux (Ubuntu 20.04+, Debian, Arch) hoặc Microsoft Windows 10/11.
  • Tài nguyên tối thiểu: CPU 1.0 GHz, RAM 64 MB, dung lượng ổ cứng khả dụng 10 MB.
  • Biên dịch và chạy ứng dụng:
# Biên dịch toàn bộ mã nguồn với trình biên dịch G++
g++ -std=c++17 -O2 main.cpp QuanLi.cpp Hoadon.cpp Khachhang.cpp Xe.cpp Xemay.cpp XeOto.cpp -o QuanLyThueXe

# Khởi chạy chương trình
./QuanLyThueXe

Phân tích hiệu quả kinh tế (ROI & Cost-Benefit)

  • Chi phí đầu tư hệ thống: 0 VNĐ chi phí bản quyền phần mềm.
  • Tiết kiệm thời gian vận hành: Giảm 85% thời gian tra cứu hồ sơ và tính toán hóa đơn so với phương pháp thủ công.
  • Loại bỏ thất thoát: Giảm thiểu 100% lỗi tính sai đơn giá giờ và lỗi cho thuê trùng xe, ước tính bảo toàn 3.000.000 – 7.000.000 VNĐ thất thoát mỗi tháng cho một cửa hàng quy mô 30 xe.

Hạn chế và hướng phát triển

Hạn chế kỹ thuật

  1. Giao diện người dùng: Ứng dụng xây dựng trên nền Console CUI, việc nhập liệu dễ gặp lỗi định dạng nếu người dùng nhập khoảng trắng hoặc ký tự đặc biệt sai vị trí.
  2. Độ phức tạp thuật toán tìm kiếm: Thuật toán tìm kiếm tuần tự (Linear Search) có độ phức tạp thời gian $O(n)$, khi quy mô dữ liệu vượt quá $50.000$ bản ghi sẽ làm suy giảm tốc độ xử lý.
  3. Cơ chế lưu trữ thô: Tập tin văn bản list.txt lưu trữ dưới dạng plain-text, chưa hỗ trợ mã hóa bảo mật thông tin định danh khách hàng (CCCD, SĐT).

Lộ trình nâng cấp hệ thống (Roadmap)

  • Ngắn hạn (1–3 tháng): Tái cấu trúc cơ chế tìm kiếm sang Cây nhị phân tìm kiếm cân bằng (AVL Tree) hoặc Bảng băm (Hash Table) nhằm đưa chi phí tìm kiếm về $O(\log n)$ hoặc $O(1)$.
  • Trung hạn (3–6 tháng): Phát triển giao diện đồ họa trực quan (GUI) bằng Framework Qt6 C++ hoặc wxWidgets, bổ sung module bẫy lỗi ngoại lệ try-catch toàn diện cho dữ liệu đầu vào.
  • Dài hạn (6–12 tháng): Thay thế tệp tin tuần tự bằng hệ quản trị cơ sở dữ liệu nhúng SQLite3, tích hợp RESTful API cho phép đồng bộ hóa dữ liệu lên ứng dụng di động của khách hàng.

Đối tượng hưởng lợi

  • Sinh viên ngành CNTT/KTPM: Nguồn tài liệu tham khảo chất lượng cao về phương pháp hiện thực cấu trúc dữ liệu con trỏ (Doubly Linked List template) và áp dụng kiến trúc hướng đối tượng OOP trong đồ án môn học.
  • Lập trình viên C++: Mô hình mẫu về việc quản lý bộ nhớ thủ công, nạp chồng toán tử I/O (friend ostream& operator<<), và xử lý con trỏ đa hình (polymorphic pointers).
  • Chủ cơ sở kinh doanh thuê xe: Giải pháp tin học hóa quản lý miễn phí, nhỏ gọn, ổn định, hoạt động độc lập không phụ thuộc Internet.
  • Nhà nghiên cứu / Giảng viên: Khung bài tập lớn thực hành (PBL) chuẩn mực để đánh giá năng lực tư duy thuật toán và kỹ năng lập trình của sinh viên.

Câu hỏi thường gặp

1. Hệ thống có yêu cầu cài đặt phần mềm quản trị CSDL chuyên dụng không?

Không. Hệ thống sử dụng trực tiếp cơ chế File Stream của C++ (ifstream, ofstream) để đọc và ghi dữ liệu ra tệp tin list.txt. Ứng dụng chạy hoàn toàn độc lập mà không cần cài đặt các dịch vụ cơ sở dữ liệu cồng kềnh như MySQL hay SQL Server.

2. Giới hạn lưu trữ tối đa của hệ thống là bao nhiêu bản ghi?

Do danh sách liên kết đôi sử dụng cơ chế cấp phát động trên vùng nhớ Heap, số lượng phương tiện, khách hàng và hóa đơn chỉ bị giới hạn bởi dung lượng RAM vật lý của thiết bị. Với 1GB RAM khả dụng, hệ thống có thể lưu trữ hơn 2.000.000 bản ghi dữ liệu hoạt động.

3. Làm thế nào để mở rộng thêm các loại phương tiện mới như xe đạp điện hoặc xe tải?

Nhờ tính chất trừu tượng và kế thừa của OOP, lập trình viên chỉ cần tạo lớp mới kế thừa từ lớp cơ sở Xe (ví dụ class XeDien : public Xe), sau đó hiện thực hóa (override) hai phương thức thuần ảo inthongtin()tinhgiathue() theo quy tắc nghiệp vụ riêng.

4. Chương trình xử lý bài toán rò rỉ bộ nhớ (Memory Leak) như thế nào?

Mọi khối nhớ cấp phát qua toán tử new trong Vector<T> đều được giải phóng triệt để thông qua phương thức clear() được gọi tự động trong hàm hủy (Destructor ~Vector()). Khi đối tượng QuanLi kết thúc phạm vi hoạt động, toàn bộ các Node liên kết đôi đều được thu hồi bộ nhớ.

5. Chi phí triển khai và thời gian hoàn vốn (ROI) của hệ thống là bao lâu?

Chi phí phần mềm là 0 VNĐ. Nếu ứng dụng cho một cửa hàng kinh doanh thuê xe thông thường, thời gian hoàn vốn là ngay lập tức nhờ loại bỏ hoàn toàn các tổn thất do tính nhầm hóa đơn và trùng lịch cho thuê.


Kết luận

Đồ án Cơ sở Lập trình "Quản lý dịch vụ cho thuê xe" đã giải quyết thành công bài toán chuyển đổi số nghiệp vụ cho thuê phương tiện tự lái. Dự án chứng minh tính hiệu quả vượt trội của việc kết hợp cấu trúc dữ liệu tự xây dựng (Vector Doubly Linked List) cùng 4 đặc tính hướng đối tượng trong C++. Hệ thống không chỉ đáp ứng hoàn hảo các yêu cầu chức năng từ quản lý đội xe, hồ sơ khách hàng đến kiểm soát xung đột hóa đơn, mà còn thiết lập nền tảng kỹ thuật vững chắc để tiếp tục mở rộng lên các nền tảng ứng dụng hiện đại hơn trong tương lai.