Bối cảnh và vấn đề nghiên cứu

Hằng năm, công tác tuyển sinh đại học và cao đẳng là một quy trình quy mô lớn với số lượng hồ sơ dự thi từ hàng ngàn thí sinh, đăng ký vào nhiều khối thi, ngành học và các cơ sở đào tạo khác nhau trên cả nước. Việc quản lý thủ công hoặc sử dụng các công cụ bảng tính đơn giản dễ phát sinh sai sót, thiếu tính đồng bộ và khó khăn trong các khâu tra cứu, thống kê, xét tuyển điểm chuẩn.

Đề tài "Quản lý tuyển sinh đại học" được thực hiện bởi sinh viên Hoàng Văn Dũng (lớp CNTT5.k22, Khoa Công nghệ Thông tin - Trường Đại học Hải Phòng) dưới sự hướng dẫn của các giảng viên bộ môn: Lê Văn Sang, Nguyễn Văn Quang và Bùi Minh Tuân, trong khuôn khổ môn học Lập trình trực quan.

Mục tiêu và nhiệm vụ nghiên cứu của đề tài bao gồm:

  1. Phân tích bài toán quản lý kỳ thi tuyển sinh gồm hai giai đoạn: tổ chức thi và sử dụng kết quả thi để xét tuyển đại học.
  2. Xây dựng mô hình hướng đối tượng mô phỏng các thực thể chính trong hệ thống quản lý tuyển sinh: thí sinh, nguyện vọng đăng ký và giám thị coi thi.
  3. Thiết kế các thuật toán xử lý dữ liệu nghiệp vụ: cập nhật thông tin (thêm, sửa, xóa), xét tuyển thí sinh trúng tuyển theo ngành và điểm chuẩn, sắp xếp điểm xét tuyển, lọc giám thị theo địa bàn công tác.
  4. Triển khai cài đặt phần mềm bằng ngôn ngữ Java (package bt.quanlituyensinhdh) và xây dựng bộ kiểm thử chức năng hoàn chỉnh.

Đối tượng nghiên cứu của đồ án là cấu trúc dữ liệu và quy trình quản lý thông tin thí sinh, danh sách nguyện vọng xét tuyển và giám thị coi thi. Phạm vi nghiên cứu tập trung vào mô hình ứng dụng tuyển sinh cấp cơ sở, xử lý dữ liệu nhập xuất trên luồng điều khiển dòng lệnh, kết hợp lưu trữ và đọc dữ liệu qua tệp nhị phân (Serializable).

Cơ sở lý thuyết và phương pháp

Đề tài ứng dụng các nguyên lý cốt lõi của lập trình hướng đối tượng (Object-Oriented Programming - OOP) trên nền tảng ngôn ngữ Java, bao gồm:

  • Tính đóng gói (Encapsulation): Khai báo các thuộc tính ở phạm vi riêng tư (private), truy xuất và cập nhật thông qua hệ thống các phương thức Getter/Setter và hàm tạo (Constructor).
  • Tính kế thừa (Inheritance): Thiết lập lớp cơ sở trừu tượng hóa Nguoi chứa các thông tin dùng chung; hai lớp con ThiSinh và GiamThi kế thừa trực tiếp từ lớp Nguoi nhằm tái sử dụng mã nguồn và thể hiện mối quan hệ phân cấp.
  • Tính đa hình (Polymorphism): Sử dụng danh sách động ArrayList<Nguoi> để lưu trữ và quản lý đồng thời cả hai đối tượng con ThiSinh và GiamThi. Quá trình duyệt danh sách và gọi phương thức ghi đè (@Override) được thực thi linh hoạt tại thời điểm chạy (runtime).
  • Cơ chế lưu trữ đối tượng (Serialization): Triển khai giao diện java.io.Serializable cùng các luồng ObjectOutputStream và ObjectInputStream để chuyển đổi trạng thái đối tượng trong bộ nhớ thành tệp nhị phân và ngược lại.

Phương pháp nghiên cứu và phát triển được áp dụng là phương pháp thiết kế và cài đặt hệ thống phần mềm:

  • Phương pháp phân tích - thiết kế hướng đối tượng: Xác định thực thể, thuộc tính, mối quan hệ kế thừa và quan hệ bao chứa (composition) giữa thí sinh và danh sách nguyện vọng (ArrayList<NguyenVong>).
  • Phương pháp thuật toán: Xây dựng các thuật toán tìm kiếm tuần tự theo khóa định danh (SBD, mã giám thị, mã nguyện vọng), thuật toán lọc dữ liệu kết hợp kiểm tra kiểu thực thể bằng toán tử instanceof, và thuật toán sắp xếp dựa trên giao diện chuẩn java.util.Comparator.
  • Nguồn dữ liệu: Dữ liệu thử nghiệm được khởi tạo trực tiếp từ bàn phím qua đối tượng java.util.Scanner và dữ liệu tệp nhị phân được lưu/đọc trực tiếp trên hệ thống tệp cục bộ.

Thiết kế và triển khai hệ thống

Hệ thống được thiết kế theo cấu trúc module phân tầng trong package bt.quanlituyensinhdh, bao gồm các lớp thực thể dữ liệu, lớp hỗ trợ thuật toán sắp xếp, lớp quản trị nghiệp vụ và lớp giao diện điều khiển chính (Main).

Cấu trúc các lớp đối tượng

Tên lớp Kế thừa / Triển khai Thuộc tính chính Phương thức chính
Nguoi Serializable hoTen, queQuan, namSinh, gioiTinh Nguoi(), getHoTen(), setHoTen(), getQueQuan(), setQueQuan(), getNamSinh(), setNamSinh(), getGioiTinh(), setGioiTinh(), nhap(), hien()
ThiSinh extends Nguoi SBD, diemUuTien, ArrayList<NguyenVong> nv, nguyenvonga ThiSinh(), getSBD(), setSBD(), getDiemUuTien(), setDiemUuTien(), getNv(), setNv(), nhap(), hien(), nhapDSNguyenVong(), hienDSNguyenVong(), hienThongTinTS()
GiamThi extends Nguoi maGT, donviCT GiamThi(), getMaGT(), setMaGT(), getDonviCT(), setDonviCT(), nhap(), hien()
NguyenVong Serializable maNv, maNganh, maTruong, tenNganh, khoiXT, diemThi NguyenVong(), getters/setters cho từng trường, getDiemXetTuyen(), nhapNguyenVong(), hienNguyenVong()
SapXepTheoDiemThi implements Comparator<NguyenVong> Không có compare(NguyenVong a1, NguyenVong a2)
QuanLy Không ArrayList<Nguoi> person, ArrayList<ThiSinh> dsTrungTuyenNganh, ArrayList<NguyenVong> nvTrungTuyen themDSNguoi(), menuSuaDoi(), SuaDoi(), suaNguyenVong(), xoaNguyenVong(), themNguyenVong(), suaThiSinh(), xoaThiSinh(), suaGiamThi(), xoaGiamThi(), hienDS(), hienDSGiamThi(), hienDSHoSoThiSinh(), hienDSThiSinh(), ghiFile(), docFile(), hienDSTrungTuyen(), SapXepTheoDiem()
Main Không Chứa luồng thực thi main(String[] args) Khởi tạo menu điều khiển chính và xử lý vòng lặp lựa chọn tính năng qua switch-case

Quy trình nghiệp vụ và thuật toán

Hệ thống xử lý các tác vụ chính thông qua 4 thuật toán trọng tâm:

  1. Thuật toán chỉnh sửa thông tin:

    • Hệ thống yêu cầu người dùng nhập khóa định danh tương ứng: Số báo danh (SBD) đối với thí sinh, mã giám thị (maGT) đối với giám thị, hoặc mã nguyện vọng (maNv) kèm SBD đối với nguyện vọng.
    • Sử dụng vòng lặp duyệt qua danh sách đối tượng và kiểm tra điều kiện trùng khớp khóa:
      • Nếu khớp: Tiến hành thao tác sửa đổi (nhập đè thông tin mới) hoặc xóa đối tượng khỏi danh sách bằng phương thức ArrayList.remove().
      • Nếu không khớp: Hệ thống kết thúc tìm kiếm mà không thực hiện thay đổi.
  2. Thuật toán xét tuyển thí sinh trúng tuyển theo ngành và điểm chuẩn:

    • Đầu vào: Người dùng nhập maNganh và diemChuan.
    • Xử lý: Duyệt danh sách thí sinh, kiểm tra từng nguyện vọng của thí sinh. Nếu nguyện vọng có mã ngành trùng với maNganh nhập vào và diemThi (hoặc điểm xét tuyển sau khi cộng điểm ưu tiên) lớn hơn hoặc bằng diemChuan, thông tin thí sinh và nguyện vọng tương ứng sẽ được lưu vào danh sách trúng tuyển dsTrungTuyenNganh và nvTrungTuyen.
  3. Thuật toán sắp xếp danh sách trúng tuyển giảm dần theo điểm thi:

    • Sử dụng lớp SapXepTheoDiemThi triển khai giao diện Comparator<NguyenVong>.
    • Phương thức compare(NguyenVong a1, NguyenVong a2) thực hiện tính hiệu số điểm xét tuyển giữa các nguyện vọng trúng tuyển (sub = a1.getDiemXetTuyen() - a2.getDiemXetTuyen()) để xác định thứ tự giảm dần thông qua hàm Collections.sort().
  4. Thuật toán thống kê giám thị quê quán Hà Nội:

    • Duyệt tập hợp ArrayList<Nguoi> person.
    • Sử dụng toán tử instanceof để lọc các đối tượng thuộc lớp GiamThi.
    • Sử dụng phương thức so sánh chuỗi không phân biệt hoa thường (compareToIgnoreCase hoặc equalsIgnoreCase) giữa thuộc tính queQuan của giám thị với chuỗi "Ha Noi". Các bản ghi thỏa mãn điều kiện sẽ được xuất ra màn hình.
  5. Cơ chế lưu và đọc tệp dữ liệu:

    • Phương thức ghiFile(String tenfile): Mở luồng FileOutputStream kết hợp ObjectOutputStream để tuần tự hóa toàn bộ danh sách person thành tệp nhị phân trên đĩa cứng.
    • Phương thức docFile(String tenfile): Khởi tạo luồng FileInputStream và ObjectInputStream để giải tuần tự hóa dữ liệu từ tệp, tái tạo lại danh sách ArrayList<Nguoi> trong bộ nhớ làm việc.

Nội dung chính theo từng chương

Phần I: Phát biểu bài toán

Phần này phân tích tổng quan bối cảnh tuyển sinh đại học, cao đẳng với khối lượng thí sinh lớn và nhiều nguyện vọng phức tạp. Tác giả mô tả bài toán thông qua quy trình hai giai đoạn: tổ chức thi và xét tuyển kết quả. Các yêu cầu nghiệp vụ đặt ra bao gồm việc quản lý tập trung ba thực thể:

  • Thí sinh: quản lý số báo danh duy nhất, thông tin nhân thân, điểm thi và điểm ưu tiên.
  • Nguyện vọng: mỗi thí sinh có quyền đăng ký nhiều nguyện vọng với mã ngành, mã trường, tên ngành, khối xét tuyển và điểm thi riêng.
  • Giám thị: quản lý mã định danh duy nhất, đơn vị công tác và thông tin cá nhân. Tác giả xác định phương án kế thừa khi nhận thấy sự tương đồng về thông tin nhân thân (họ tên, năm sinh, quê quán, giới tính) giữa thí sinh và giám thị, đồng thời ứng dụng cấu trúc danh sách tổng quát ArrayList<Nguoi> để quản lý đa hình.

Phần II: Xác định các lớp của bài toán

Phần II quy định chi tiết cấu trúc hướng đối tượng của hệ thống, bao gồm 5 lớp cốt lõi:

  • Lớp Nguoi: Lớp cha cơ sở, mô hình hóa các thuộc tính định danh cá nhân cơ bản và định nghĩa phương thức nhap(), hien().
  • Lớp ThiSinh: Kế thừa lớp Nguoi, mở rộng các thuộc tính học thuật như SBD, diemUuTien, danh sách liên kết ArrayList<NguyenVong> nv. Ghi đè phương thức nhap(), hien() để bao hàm cả việc nhập/xuất danh sách nguyện vọng.
  • Lớp GiamThi: Kế thừa lớp Nguoi, bổ sung các thông tin nghiệp vụ gồm maGT và donviCT.
  • Lớp NguyenVong: Lớp độc lập mô tả chi tiết thông tin tuyển sinh từng ngành của thí sinh, hỗ trợ tính toán điểm xét tuyển.
  • Lớp QuanLy: Đóng vai trò lớp điều phối trung tâm, chứa danh sách tổng hợp person kiểu ArrayList<Nguoi>, cùng các danh sách trúng tuyển dsTrungTuyenNganh và nvTrungTuyen, tích hợp hệ thống hàm xử lý thêm, sửa, xóa, tìm kiếm, sắp xếp và đọc/ghi file.

Phần III: Mô tả thuật toán thao tác

Phần III trình bày logic các thuật toán cốt lõi điều khiển toàn bộ chức năng của chương trình:

  • Thuật toán tìm kiếm và chỉnh sửa đối tượng (thí sinh, giám thị, nguyện vọng) dựa trên khóa định danh và thao tác trên mảng động ArrayList.
  • Thuật toán lọc thí sinh trúng tuyển theo tham số đầu vào là mã ngành và điểm chuẩn sàn.
  • Thuật toán sắp xếp nguyện vọng trúng tuyển theo thứ tự điểm giảm dần sử dụng Collections.sort và lớp so sánh SapXepTheoDiemThi.
  • Thuật toán thống kê giám thị có quê quán tại Hà Nội sử dụng kiểm tra kiểu động instanceof và so khớp chuỗi không phân biệt ký tự hoa/thường.

Phần IV: Cài đặt bài toán và kiểm thử

Phần IV thể hiện toàn bộ mã nguồn cài đặt các lớp bằng Java trong gói bt.quanlituyensinhdh:

  • Cài đặt chi tiết các lớp Nguoi, ThiSinh, NguyenVong, GiamThi, SapXepTheoDiemThi, DSNguoi và QuanLy.
  • Cài đặt hệ thống menu tương tác phân cấp tại lớp QuanLy và lớp Main, cung cấp menu chức năng chính gồm 10 tùy chọn và menu con menuSuaDoi gồm 7 tùy chọn chỉnh sửa chi tiết.
  • Thiết lập quy trình kiểm thử thông qua giao diện dòng lệnh, bao gồm kiểm thử nhập liệu đa hình, kiểm thử logic xét tuyển, kiểm thử sắp xếp và kiểm thử ghi/đọc dữ liệu tệp tin.

Kết quả và đóng góp

Kết quả đạt được

Hệ thống đã triển khai đầy đủ các tính năng theo đúng mục tiêu thiết kế ban đầu:

  • Xây dựng thành công hệ thống phân cấp lớp kế thừa rõ ràng, quản lý dữ liệu thí sinh và giám thị thông qua một cấu trúc danh sách duy nhất ArrayList<Nguoi>.
  • Hiện thực hóa đầy đủ menu điều khiển chính gồm 10 chức năng nghiệp vụ:
    1. Nhập danh sách thí sinh và nguyện vọng của thí sinh.
    2. Nhập danh sách giám thị coi thi.
    3. Hiển thị danh sách hồ sơ dự thi (bao gồm thông tin cá nhân và danh sách nguyện vọng).
    4. Hiển thị danh sách giám thị.
    5. Chỉnh sửa thông tin (truy cập menu con cho phép sửa/xóa thí sinh, giám thị, nguyện vọng).
    6. Lưu danh sách đối tượng đã nhập vào tệp dữ liệu nhị phân.
    7. Đọc và khôi phục dữ liệu từ tệp nhị phân vào bộ nhớ.
    8. Tra cứu và xuất danh sách thí sinh trúng tuyển theo mã ngành và điểm chuẩn.
    9. Sắp xếp danh sách thí sinh trúng tuyển theo điểm thi giảm dần.
    10. Thống kê và hiển thị danh sách giám thị có quê quán tại Hà Nội.
  • Đảm bảo cơ chế lưu trữ bền vững (persistence) cho dữ liệu đối tượng thông qua cơ chế Java Object Serialization.

Đóng góp của đề tài

  • Đề xuất giải pháp quản lý thực thể linh hoạt bằng cách áp dụng tính đa hình trong Java, giúp thu gọn cấu trúc lưu trữ và tối ưu hóa quy trình nhập/xuất dữ liệu nhân sự kỳ thi.
  • Mô hình hóa thành công quan hệ 1-N (một thí sinh có nhiều nguyện vọng) thông qua việc nhúng danh sách ArrayList<NguyenVong> bên trong thuộc tính của lớp ThiSinh.
  • Xây dựng một cấu trúc mã nguồn hoàn chỉnh, phân chia rõ ràng giữa thực thể dữ liệu (Model), thuật toán xử lý (Business Logic) và luồng điều khiển tương tác (Console Interface).

Hạn chế và hướng nghiên cứu tiếp

Hạn chế

  • Giao diện người dùng: Ứng dụng mới chỉ dừng lại ở giao diện dòng lệnh console (nhập xuất qua Scanner và System.out.print), chưa xây dựng giao diện đồ họa người dùng trực quan (GUI như Java Swing hay JavaFX) dù nằm trong môn học Lập trình trực quan.
  • Lưu trữ dữ liệu: Việc sử dụng tệp nhị phân (ObjectOutputStream/ObjectInputStream) chỉ phù hợp với tập dữ liệu nhỏ; chưa tích hợp hệ quản trị cơ sở dữ liệu quan hệ (RDBMS như MySQL, SQL Server) để xử lý dữ liệu lớn và truy vấn đồng thời.
  • Kiểm soát ràng buộc và ngoại lệ: Cơ chế xử lý ngoại lệ (Exception Handling) còn cơ bản, chưa có các ràng buộc chặt chẽ về định dạng điểm số, định dạng ngày tháng năm sinh hoặc trùng lặp mã định danh khi thêm mới.

Hướng nghiên cứu và phát triển tiếp

  • Phát triển giao diện trực quan hoàn chỉnh bằng Java Swing, JavaFX hoặc xây dựng ứng dụng web quản lý tuyển sinh.
  • Chuyển đổi phương thức lưu trữ dữ liệu từ tệp nhị phân sang cơ sở dữ liệu quan hệ kết nối qua JDBC hoặc hệ thống ORM (Hibernate).
  • Bổ sung các tính năng nâng cao: phân quyền tài khoản (quản trị viên, giám thị, thí sinh), tự động tính điểm chuẩn theo chỉ tiêu tuyển sinh, và xuất báo cáo dưới dạng định dạng PDF hoặc Excel.

Giá trị tham khảo

Đồ án là tài liệu tham khảo hữu ích cho:

  • Sinh viên chuyên ngành Công nghệ thông tin, Kỹ thuật phần mềm đang học các học phần Lập trình hướng đối tượng (OOP), Lập trình Java, Lập trình trực quan.
  • Người học cần tài liệu mẫu về thiết kế kiến trúc phân cấp lớp (kế thừa, đa hình), thao tác xử lý tập hợp (ArrayList, Collections.sort, Comparator) và xử lý tệp đối tượng (Serialization) trong Java.
  • Sinh viên thực hiện các bài tập lớn, đồ án môn học có đề tài về quản lý nhân sự, quản lý hồ sơ tuyển sinh hoặc quản lý đào tạo cấp trường.

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

1. Thuộc tính gioiTinh trong lớp Nguoi được thiết kế và hiển thị như thế nào?

Thuộc tính gioiTinh được lưu trữ dưới dạng số nguyên (int). Trong phương thức getGioiTinh(), giá trị 1 được quy đổi và hiển thị thành chuỗi "Nam", giá trị 0 được quy đổi thành "Nữ", và trả về null nếu nhận giá trị khác.

2. Tính đa hình trong việc quản lý thí sinh và giám thị được triển khai cụ thể ra sao?

Hệ thống sử dụng một danh sách duy nhất ArrayList<Nguoi> person trong lớp QuanLy. Danh sách này có thể chứa đồng thời các đối tượng thuộc lớp ThiSinh và GiamThi (do cả hai đều kế thừa từ lớp Nguoi). Khi duyệt danh sách, chương trình tự động gọi phương thức hien() hoặc nhap() tương ứng với từng kiểu đối tượng thực tế tại thời điểm chạy.

3. Làm thế nào để lọc ra các giám thị có quê quán tại Hà Nội từ danh sách chung?

Chương trình duyệt qua danh sách ArrayList<Nguoi> person, sử dụng toán tử instanceof để kiểm tra đối tượng có phải là kiểu GiamThi hay không. Nếu đúng, chương trình lấy thông tin quê quán và sử dụng phương thức so sánh chuỗi không phân biệt chữ hoa/chữ thường (compareIgnoreCase/equalsIgnoreCase) với chuỗi "Ha Noi" để xuất kết quả.

4. Hệ thống sắp xếp danh sách trúng tuyển theo điểm thi bằng cơ chế nào?

Chương trình định nghĩa lớp SapXepTheoDiemThi triển khai giao diện Comparator<NguyenVong> với phương thức compare(NguyenVong a1, NguyenVong a2). Phương thức này so sánh điểm xét tuyển của hai nguyện vọng và được truyền vào hàm Collections.sort() để sắp xếp danh sách nvTrungTuyen theo thứ tự điểm giảm dần.

5. Dữ liệu của hệ thống được lưu trữ và khôi phục bằng công nghệ gì?

Hệ thống sử dụng cơ chế Java Object Serialization. Các lớp Nguoi và NguyenVong đều triển khai giao diện java.io.Serializable. Lớp QuanLy sử dụng FileOutputStream kết hợp ObjectOutputStream trong phương thức ghiFile() để lưu danh sách đối tượng, và sử dụng FileInputStream cùng ObjectInputStream trong phương thức docFile() để khôi phục dữ liệu từ tệp nhị phân.

Kết luận

Báo cáo bài tập lớn môn Lập trình trực quan của sinh viên Hoàng Văn Dũng đã giải quyết thành công bài toán quản lý tuyển sinh đại học ở mức độ thiết kế hướng đối tượng hoàn chỉnh. Tác giả đã vận dụng tốt các nguyên lý cốt lõi của ngôn ngữ Java như tính kế thừa, tính đa hình, xử lý cấu trúc dữ liệu danh sách động và cơ chế tuần tự hóa tệp tin. Đồ án cung cấp cấu trúc mã nguồn rõ ràng, đáp ứng đầy đủ các yêu cầu nghiệp vụ từ khâu tiếp nhận hồ sơ, chỉnh sửa thông tin, tra cứu điểm chuẩn cho đến thống kê và lưu trữ dữ liệu.