Thiết kế lớp thừa kế để tính điểm tổng kết môn C++

Trong bài toán này, chúng ta sẽ xây dựng một hệ thống phân cấp lớp nhằm quản lý và tính toán điểm tổng kết của sinh viên. Yêu cầu bắt đầu từ việc định nghĩa lớp cơ sở, sau đó dẫn xuất lớp con để bổ sung các thuộc tính điểm số và phương thức xử lý cụ thể.

1. Định nghĩa lớp cơ sở và lớp dẫn xuất

Lớp cơ sở sẽ chứa các thông tin chung gồm tên và tuổi, được khai báo ở phạm vi protected để lớp con có thể kế thừa và truy cập trực tiếp. Lớp con kế thừa công khai, đồng thời bổ sung các trường dữ liệu sau:

  • maSinhVien: Mã số sinh viên (kiểu int)
  • diemThucHanh: Điểm làm bài thực hành (kiểu float)
  • soTietChi: Số tiết học sinh đã tham gia (kiểu float)
  • diemTongKet: Điểm tổng kết cuối cùng (kiểu float)

Quy tắc tính điểm tổng kết được quy định như sau:

diemTongKet = diemThucHanh * 0.9 + soTietChi * 2.0

2. Yêu cầu về phương thức

  • Hàm tạo mặc định không tham số.
  • Hàm tạo có tham số nhận đầy đủ thông tin cá nhân và điểm số. Giá trị điểm tổng kết sẽ được tính toán ngay khi đối tượng được khởi tạo.
  • Phương thức xuatThongTin() dùng để in ra console dòng kết quả theo định dạng: maSinhVien ten diemTongKet. Điểm tổng kết phải được hiển thị chính xác 1 chữ số thập phân.

3. Quy tắc nhập xuất dữ liệu

Chương trình sẽ đọc dữ liệu từ dòng lệnh theo từng dòng, mỗi dòng tương ứng với một sinh viên với định dạng: Tên MãSV Tuổi ĐiểmThucHanh SốTietChi. Vòng lặp nhập liệu sẽ kết thúc khi giá trị của trường Tên là ký tự 0. Dòng dữ liệu tương ứng với trường hợp kết thúc không được xử lý hay in ra.

Ví dụ đầu vào:

NguyenVanA 2024001 20 80.5 3
TranVanB 2024005 19 90.0 5
0

Ví dụ đầu ra:

2024001 NguyenVanA 84.5
2024005 TranVanB 95.0

4. Triển khai mã nguồn

Dưới đây là giải pháp hoàn chỉnh. Mã nguồn đã được tái cấu trúc để tăng tính rõ ràng, sử dụng initializer list và tách biệt logic tính toán.

#include <iostream>
#include <iomanip>
#include <string>

using namespace std;

class Nguoi {
protected:
    string hoTen;
    int tuoi;
public:
    Nguoi() : hoTen(""), tuoi(0) {}
    Nguoi(string ten, int t) : hoTen(ten), tuoi(t) {}
    void hienThi() const {
        cout << hoTen << " - " << tuoi << endl;
    }
};

class SinhVien : public Nguoi {
private:
    int maSV;
    float diemThi;
    float soTiet;
    float diemTB;

public:
    SinhVien() : Nguoi(), maSV(0), diemThi(0.0f), soTiet(0.0f), diemTB(0.0f) {}

    SinhVien(string ten, int t, int m, float d, float s) 
        : Nguoi(ten, t), maSV(m), diemThi(d), soTiet(s) {
        tinhDiem();
    }

    void xuatThongTin() const {
        cout << maSV << " " << hoTen << " " 
             << fixed << setprecision(1) << diemTB << endl;
    }

private:
    void tinhDiem() {
        diemTB = (diemThi * 0.9f) + (soTiet * 2.0f);
    }
};

int main() {
    string tenNhap;
    cin >> tenNhap;

    while (tenNhap != "0") {
        int ma, tuoi;
        float diem, tiet;
        cin >> ma >> tuoi >> diem >> tiet;

        SinhVien sinhVien(tenNhap, tuoi, ma, diem, tiet);
        sinhVien.xuatThongTin();

        cin >> tenNhap;
    }

    return 0;
}

Thẻ: C++ oop Class Inheritance Standard Library

Đăng vào ngày 17 tháng 9 lúc 14:20