Trước khi đi vào bài tập struct trong C/C++, LTKK muốn tóm tắt về kiểu cấu trúc trong C. Kiểu cấu trúc (structure) trong C/C++ là 1 kiểu dữ liệu người dùng tự định nghĩa dựa trên các kiểu dữ liệu có sẵn (int, char*, float, …). Chúng ta thường dùng kiểu cấu trúc này để định nghĩa các đối tượng. Ví dụ:
- Đối tượng Sinh Viên: mã sinh viên (char*), tên sinh viên (char*), năm sinh (int), …
- Đối tượng Date: ngày (int), tháng (int), năm (int).
- Đối tượng Sách: mã sách (char*), tên sách (char*), tác giả (char*), số lượng (int), ngày xuất bản (Date), …
LTKK đã có 1 bài viết riêng hướng dẫn về kiểu cấu trúc trong C/C++. Bạn nên có kiến thức về Struct trong C trước khi thực hành bài tập struct tại bài viết này.
Bài tập struct trong C/C++
Kiểu cấu trúc (struct) là của ngôn ngữ lập trình C, do đó chúng ta có thể sử dụng nó ở trong C++. Trong mục bài tập này, mình sẽ cố gắng chỉ sử dụng ngôn ngữ C. Nếu có phần nào trong source code sử dụng C++, mình sẽ trình bày rõ.
# Bài tập phân số
Đề bài: Định nghĩa kiểu cấu trúc phân số gồm tử số và mẫu số. Thực hiện cài đặt các chức năng sau:
- Cài đặt các phép toán cộng, trừ, nhân, chia 2 phân số.
- In ra kết quả các phép toán kể trên dưới dạng phân số tối giản.
Lời giải:
Dưới đây là lời giải tham khảo sử dụng ngôn ngữ C.
#include <stdio.h>
#include <string.h>
#include <math.h>
int UCLN(int a, int b)
{
a = abs(a);
b = abs(b);
while (a * b != 0)
{
if (a > b)
a %= b;
else
b %= a;
}
return a + b;
}
int BSCNN(int a, int b)
{
return a * b / UCLN(a, b);
}
typedef struct PhanSo
{
int tuso, mauso;
} PS;
PS rutGon(PS a)
{
PS c;
c.tuso = a.tuso / UCLN(a.tuso, a.mauso);
c.mauso = a.mauso / UCLN(a.tuso, a.mauso);
return c;
}
PS cong(PS a, PS b)
{
PS c;
c.tuso = a.tuso * b.mauso + a.mauso * b.tuso;
c.mauso = a.mauso * b.mauso;
c = rutGon(c);
return c;
}
PS tru(PS a, PS b)
{
PS c;
c.tuso = a.tuso * b.mauso - a.mauso * b.tuso;
c.mauso = a.mauso * b.mauso;
c = rutGon(c);
return c;
}
PS nhan(PS a, PS b)
{
PS c;
c.tuso = a.tuso * b.tuso;
c.mauso = a.mauso * b.mauso;
c = rutGon(c);
return c;
}
PS chia(PS a, PS b)
{
PS c;
c.tuso = a.tuso * b.mauso;
c.mauso = a.mauso * b.tuso;
c = rutGon(c);
return c;
}
void print(PS a)
{
printf("%d/%d", a.tuso, a.mauso);
}
int main()
{
PS a, b, c;
printf("nNhap phan so a : ");
scanf("%d%d", &a.tuso, &a.mauso);
printf("nNhap phan so b : ");
scanf("%d%d", &b.tuso, &b.mauso);
printf("nToi gian a ta duoc : ");
a = rutGon(a);
print(a);
printf("nToi gian b ta duoc : ");
b = rutGon(b);
print(b);
printf("nTong cua hai phan so = ");
c = cong(a, b);
print(c);
printf("nHieu cua hai phan so = ");
c = tru(a, b);
print(c);
printf("nTich cua hai phan so = ");
c = nhan(a, b);
print(c);
printf("nThuong cua hai phan so = ");
c = chia(a, b);
print(c);
}Kết quả chạy chương trình:
Nhap phan so a : 1 2 Nhap phan so b : 3 4 Toi gian a ta duoc : 1/2 Toi gian b ta duoc : 3/4 Tong cua hai phan so = 5/4 Hieu cua hai phan so = -1/4 Tich cua hai phan so = 3/8 Thuong cua hai phan so = 2/3
# Bài tập quản lý sinh viên
Mục tiêu của bài tập này là sử dụng cấu trúc struct lồng nhau.
Đề bài: Viết chương trình định nghĩa kiểu cấu trúc NGAYTHANG bao gồm 3 thuộc tính (ngày, tháng, năm). Dựa trên kiểu cấu trúc NGAYTHANG đã có, tiếp tục định nghĩa kiểu câu trúc SinhVien bao gồm các thông tin (mã sinh viên, họ đệm, tên, ngày tháng năm sinh, giới tính, hộ khẩu thường trú, điểm thi đại học). Viết các hàm con thực hiện các chức năng sau đây:
- Nhập danh sách sinh viên từ bàn phím.
- Hiển thị danh sách sinh viên đã nhập.
- Sắp xếp danh sách sinh viên theo điểm tăng dần.
- Hiển thị danh sách sau khi sắp xếp.
Viết hàm main thực hiện các chức năng kể trên.
Lời giải tham khảo:
- Lời giải này có sử dụng C++ ở hàm nhập/xuất: cin, cout; cấp phát động trong C++ (toán tử new, delete).
- Khi dùng struct trong C++, chúng ta không cần thêm tiền tố struct khi khai báo biến. Do đó, không cần dùng từ khóa typedef để đặt lại tên kiểu cấu trúc sinh viên.
#include<iostream>
#include<stdio.h>
#include<math.h>
#include<string.h>
#include<limits>
using namespace std;
struct NGAYTHANG {
int ngay;
int thang;
int nam;
};
struct SV {
char masv[12];
char hodem[30];
char ten[10];
NGAYTHANG ngsinh;
char gioitinh[4];
char hokhau[20];
float diem;
};
void Nhapsv(SV *sv) {
cin.ignore(256, 'n');
cout << "tMa sv: ";
scanf(" %[^n]s", sv->masv);
cout << "tHo dem: ";
scanf(" %[^n]s", sv->hodem);
cout << "tTen: ";
scanf(" %[^n]s", sv->ten);
cout << "tNgay sinh: ";
cin >> sv->ngsinh.ngay;
cout << "tThang sinh: ";
cin >> sv->ngsinh.thang;
cout << "tNam sinh: ";
cin >> sv->ngsinh.nam;
cout << "tGioi tinh: ";
scanf(" %[^n]s", sv->gioitinh);
cout << "tHo khau: ";
scanf(" %[^n]s", sv->hokhau);
cout << "tDiem: ";
cin >> sv->diem;
}
void Hienthisv(SV *sv) {
cout << sv->masv;
cout << "t" << sv->hodem;
cout << " " << sv->ten;
cout << "t" << sv->ngsinh.ngay;
cout << "-" << sv->ngsinh.thang;
cout << "-" << sv->ngsinh.nam;
cout << "t" << sv->gioitinh;
cout << "t" << sv->hokhau;
cout << "t" << sv->diem;
}
void Nhapds(SV *p, int n) {
for (int i = 0; i < n; i++) {
cout << "Nhap thong tin cua sv thu " << i + 1 << " :" << endl;
Nhapsv(p + i);
}
}
void Hienthids(SV *p, int n) {
for (int i = 0; i < n; i++) {
Hienthisv(p + i);
cout << "n";
}
}
void Sapxep(SV *p, int n) {
for (int i = 0; i < n; i++) {
for (int j = i + 1; j < n; j++)
if ((p + i)->diem > (p + j)->diem) {
SV tmp = * (p + j);
*(p + j) = * (p + i);
*(p + i) = tmp;
}
}
}
int main() {
SV *p;
int n;
do {
cout << "Nhap vao so sv: ";
cin >> n;
}
while (n < 0 || n > 10);
p = new SV[n];
cout << "Nhap vao thong tin " << n << " sv: " << endl;
Nhapds(p, n);
cout << "Hien thi thong tin vua nhap: " << endl;
Hienthids(p, n);
cout << "nDanh sach sau khi sap xep la: " << endl;
Sapxep(p, n);
Hienthids(p, n);
delete p;
return 0;
}Kết quả chạy chương trình:
Nhap vao so sv: 2
Nhap vao thong tin 2 sv:
Nhap thong tin cua sv thu 1 :
Ma sv: sv001
Ho dem: Nguyen Van
Ten: Hieu
Ngay sinh: 10
Thang sinh: 10
Nam sinh: 1996
Gioi tinh: Nam
Ho khau: Ha Noi
Diem: 10
Nhap thong tin cua sv thu 2 :
Ma sv: sv002
Ho dem: Nguyen Thi
Ten: Mai
Ngay sinh: 11
Thang sinh: 11
Nam sinh: 1996
Gioi tinh: Nu
Ho khau: Nam Dinh
Diem: 9
Hien thi thong tin vua nhap:
sv001 Nguyen Van Hieu 10-10-1996 Nam Ha Noi 10
sv002 Nguyen Thi Mai 11-11-1996 Nu Nam Dinh 9
Danh sach sau khi sap xep la:
sv002 Nguyen Thi Mai 11-11-1996 Nu Nam Dinh 9
sv001 Nguyen Van Hieu 10-10-1996 Nam Ha Noi 10# Bài tập struct quản lý món ăn
Đề bài: Viết chương trình tổ chức dữ liệu quản lý các món ăn, mỗi món ăn bao gồm các thông tin sau: tên món ăn, đơn giá, đơn vị tính, loại món, …
Viết các chương trình con (hàm) thực hiện lần lượt các yêu cầu sau đây:
- Nhập danh sách n món ăn từ bàn phím.
- Hiển thị danh sách món ăn vừa nhập.
- Thực hiện sắp xếp danh sách món ăn tăng dần/ giảm dần theo 1 tiêu chí nào đó (tự lựa chọn).
- Thực hiện tìm kiếm món ăn theo tiêu chí tùy ý.
- Ghi danh sách món ăn vào tập tin.
- Đọc dữ liệu món ăn từ tập tin.
- Trích lọc thông tin món ăn theo 1 tiêu chí tùy chọn và xuất kết quả ra tệp tin.
Cài đặt chương trình chính triển khai lần lượt các chức năng kể trên.
Lời giải tham khảo:
- Trong lời giải tham khảo này có sử dụng tham chiếu của C++.
#include <stdio.h> // thư viện nhập xuất chuẩn (scanf, printf, fgets, ...)
#include <string.h> // thư viện chuỗi (strlen, strcmp, ...)
#include <stdlib.h> // dùng hàm exit và hằng số EXIT_FAILURE, EXIT_SUCCESS
// Hằng số số lượng phần tử tối đa món ăn có thể lưu
#define MAX_SIZE 100
// 2 hằng số đường dẫn file dùng cho đọc/ghi file và trích xuất thông tin
const char* DATA_PATH = "data.dat";
const char* EXTRACT_PATH = "trichloc.dat";
struct Food {
char name[50]; // tên món ăn
int price; // đơn giá
char unit[50]; // đơn vị tính
char type[50]; // loại món
};
// Thay vì khai báo struct Food <tên biến> thì chỉ cần Food <tên biến>
// ngắn gọn hơn
typedef struct Food Food;
// Hàm nhập 1 món ăn
Food createFood(){
Food food;
char temp[50];
printf("Enter food name: ");
scanf(" %[^n]s", food.name);
printf("Enter food price: ");
scanf(" %[^n]s", temp);
food.price = atoi(temp);
printf("Enter food unit: ");
scanf(" %[^n]s", food.unit);
printf("Enter food type: ");
scanf(" %[^n]s", food.type);
return food;
}
// Hàm nhập n món ăn
void createFoods(Food arr[], int n){
for (int i = 0; i < n; i++){
Food food = createFood();
arr[i] = food;
printf("-----------------n");
}
}
// Hàm in tiêu đề, phục vụ in thông tin món ăn dạng bảng (table)
void printTitle(){
printf("%20s%20s%20s%20sn", "Name", "Price", "Unit", "Type");
}
// Hàm in thông tin 1 món ăn
void printFood(Food food){
printf("%20s%20d%20s%20sn", food.name, food.price, food.unit, food.type);
}
// Hàm in ra màn hình ds món ăn
void printFoods(Food arr[], int n){
printTitle();
for (int i = 0; i < n; i++){
printFood(arr[i]);
}
}
// Hàm sắp xếp ds món ăn
// Có thể sắp xếp theo tên món hoặc giá tăng dần
void sortFood(Food arr[], int n){
int choice;
printf("Choose sort type:n1. By namen2. By pricenEnter your choice: ");
scanf("%d", &choice);
if (choice != 1 && choice != 2){
printf("Only option 1 or 2 is allow!");
return;
}
for (int i = 0; i < n; i++){
for(int j = i+1; j < n; j++){
if ((choice == 1 && strcmp(arr[i].name, arr[j].name) > 0) ||
(choice == 2 && arr[i].price > arr[j].price)) {
Food temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}
}
}
// Hàm tìm kiếm món ăn
// Có thể chọn tìm theo tên hoặc theo loại món ăn
void searchFood(Food arr[], int n){
int choice;
printf("Choose search type:n1. By namen2. By typenEnter your choice: ");
scanf("%d", &choice);
if (choice != 1 && choice != 2){
printf("Only option 1 or 2 is allow!");
return;
}
char keyword[50];
printf("Enter the search keyword: ");
scanf(" %[^n]s", keyword);
printf("Search result for keyword '%s':n", keyword);
int count = 0; // đếm số lượng kết quả tìm được
for (int i = 0; i < n; i++){
if ((choice == 0 && strcmp(keyword, arr[i].name) == 1) || (choice == 2 && strcmp(keyword, arr[i].type) == 0)) {
if (count == 0){
printTitle();
}
printFood(arr[i]);
count++;
}
}
// Nếu không tìm được kết quả nào thì thông báo ko thấy
if (count == 0){
printf("No result!n");
}
}
// Hàm ghi các món ăn ra file
void toFile(Food arr[], int n){
FILE *fptr; // con trỏ file
fptr = fopen(DATA_PATH,"w"); // mở file
if(fptr == NULL) {
printf("Error on open file for write!");
exit(EXIT_FAILURE); // thoát chương trình nếu có lỗi mở file
}
fprintf(fptr,"%dn", n); // dòng đầu tiên ghi số món ăn
for (int i = 0; i < n; i++){
// một món ăn sẽ ghi 4 dòng
fprintf(fptr, "%sn%dn%sn%sn", arr[i].name, arr[i].price, arr[i].unit, arr[i].type);
}
printf("Write %d foods to path %s successed!n", n, DATA_PATH);
fclose(fptr); // đóng file
}
// Hàm đọc món ăn từ file
// n là tham chiếu, vì ta cần thay đổi giá trị của n ở hàm main tại hàm này.
// Nếu dùng C thì có thể dùng con trỏ thay thế
void fromFile(Food arr[], int &n){
FILE *fptr;
fptr = fopen(DATA_PATH,"r");
if(fptr == NULL) {
printf("Error on open file for read!n");
exit(EXIT_FAILURE); // thoát chương trình nếu có lỗi mở file
}
fgets(arr[0].name, 50, fptr); // đọc 1 dòng
n = atoi(arr[0].name); // chuyển chuỗi về số, dòng đầu tiên là số lượng món ăn.
// Kiểm tra số món ăn trong file ko đc vượt qua MAX_SIZE, cũng ko được âm
if (n < 0 || n > MAX_SIZE){
printf("Number of foods not valid!");
exit(EXIT_FAILURE);
}
for (int i = 0; i < n; i++){
// đọc 4 dòng để lấy thông tin 1 món ăn
fgets(arr[i].name, 50, fptr);
arr[i].name[strcspn(arr[i].name, "n")] = 0; // xóa n ở cuối
fgets(arr[i].unit, 50, fptr);
arr[i].price = atoi(arr[i].unit); // chuyển chuỗi về số
fgets(arr[i].unit, 50, fptr);
arr[i].unit[strcspn(arr[i].unit, "n")] = 0;
fgets(arr[i].type, 50, fptr);
arr[i].type[strcspn(arr[i].type, "n")] = 0;
}
printf("Read %d foods from path %s successed!n", n, DATA_PATH);
fclose(fptr);
}
// Trích xuất các món ăn có giá nằm trong phạm vi x - y
void filterFood(Food arr[], int n){
int minPrice, maxPrice;
printf("Enter min price: "); scanf("%d", &minPrice);
printf("Enter max price: "); scanf("%d", &maxPrice);
// Nếu giới hạn dưới mà lớn hơn, thì hoán đổi
if (minPrice > maxPrice) {
int temp = minPrice;
minPrice = maxPrice;
maxPrice = temp;
}
// Mở file để ghi
FILE *fptr; // con trỏ file
fptr = fopen(EXTRACT_PATH,"w"); // mở file
if(fptr == NULL) {
printf("Error on open file for write!");
exit(EXIT_FAILURE); // thoát chương trình nếu có lỗi mở file
}
int count = 0; // đếm số lượng kết quả tìm được
for (int i = 0; i < n; i++){
if (arr[i].price >= minPrice && arr[i].price <= maxPrice) {
// Ghi tiêu đề
if (count == 0){
fprintf(fptr, "%20s%20s%20s%20sn", "Name", "Price", "Unit", "Type");
}
// ghi mỗi món trên 1 dòng
fprintf(fptr, "%20s%20d%20s%20sn", arr[i].name, arr[i].price, arr[i].unit, arr[i].type);
count++;
}
}
if (count == 0){
fprintf(fptr, "%s", "No result!n");
}
printf("Found %d result in price range %d to %d!n", count, minPrice, maxPrice);
fclose(fptr);
}
void printMenu(){
printf("=================== MENU ======================n");
printf("1. Create foods from keyboardn");
printf("2. Show foodsn");
printf("3. Sort foodsn");
printf("4. Search foodsn");
printf("5. Write to filen");
printf("6. Read from filen");
printf("7. Filter & extract foodsn");
printf("8. ExitnYour choice: ");
}
int main(){
Food foods[MAX_SIZE];
int n = 0, choice;
while (1){
printMenu();
scanf("%d", &choice);
if (choice < 1 || choice > 8){
printf("Please choose one option from 1 - 8!");
continue;
}
switch (choice)
{
case 1:
do {
printf("Enter number of foods: ");
scanf("%d", &n);
}while (n <= 0 || n > MAX_SIZE);
createFoods(foods, n);
break;
case 2:
if (n == 0){
printf("No data!n");
continue;
}
printFoods(foods, n);
break;
case 3:
if (n == 0){
printf("No data!n");
continue;
}
sortFood(foods, n);
printf("Foods after sorted:n");
printFoods(foods, n);
break;
case 4:
if (n == 0){
printf("No data!n");
continue;
}
searchFood(foods, n);
break;
case 5:
if (n == 0){
printf("No data!n");
continue;
}
toFile(foods, n);
break;
case 6:
fromFile(foods, n);
break;
case 7:
if (n == 0){
printf("No data!n");
continue;
}
filterFood(foods, n);
break;
case 8:
printf("Good bye!n");
exit(EXIT_SUCCESS);
}
}
}Kết quả chạy chương trình:
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 1
Enter number of foods: 3
Enter food name: 3
Enter food price: 3
Enter food unit: 3
Enter food type: 3
-----------------
Enter food name: 1
Enter food price: 1
Enter food unit: 1
Enter food type: 1
-----------------
Enter food name: 2
Enter food price: 2
Enter food unit: 2
Enter food type: 2
-----------------
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 2
Name Price Unit Type
1. 3 3 3 3
2. 1 1 1 1
3. 2 2 2 2
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 3
Choose sort type:
1. By name
2. By price
Enter your choice: 1
Foods after sorted:
Name Price Unit Type
1. 1 1 1 1
2. 2 2 2 2
3. 3 3 3 3
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 4
Choose search type:
1. By name
2. By type
Enter your choice: 2
Enter the search keyword: 2
Search result for keyword '2':
Name Price Unit Type
2 2 2 2
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 5
Write 3 foods to path data.dat successed!
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 6
Read 3 foods from path data.dat successed!
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 2
Name Price Unit Type
1. 1 1 1 1
2. 2 2 2 2
3. 3 3 3 3
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 7
Enter min price: 2
Enter max price: 3
Found 2 result in price range 2 to 3!
=================== MENU ======================
1. Create foods from keyboard
2. Show foods
3. Sort foods
4. Search foods
5. Write to file
6. Read from file
7. Filter & extract foods
8. Exit
Your choice: 8
Good bye!# Bài tập quản lý sách
Viết chương trình quản lý sách của một nhà xuất bản với thông tin của mỗi cuốn sách bao gồm: mã sách, tên sách, tác giả, nhà xuất bản, năm xuất bản, đơn giá, số lượng, thuế, thực tiền. Trong đó thành tiền và thực tiền được tính dựa trên các thông tin khác được nhập từ bàn phím. Viết chương trình con triển khai các chức năng sau:
- Nhập thông tin các cuốn sách từ bàn phím.
- In danh sách thông tin các cuốn sách.
- Tính cột thành tiền theo công thức thành tiền = số lượng * đơn giá.
- Tính cột thực tiền = thành tiền + thuế VAT
- Sắp xếp các cuốn sách theo thứ tự giảm dần về năm xuất bản.
- In thông tin các cuốn sách có thực tiền lớn nhất.
- In thông tin tổng số lượng các cuốn sách.
- In danh sách các cuốn sách có thuế VAT lớn hơn 1 giá trị được nhập từ bàn phím.
- Lưu danh sách các cuốn sách đã nhập vào tập tin.
- Đọc danh sách các cuốn sách từ tập tin và hiển thị lên màn hình.
Dưới đây là lời giải tham khảo sử dụng ngôn ngữ C++.
#include <iostream>
#include <string.h>
#include <iomanip>
#include <stdlib.h>
using namespace std;
const int MAX_SIZE = 100; // số lượng phần tử tối đa của mảng
const char* DATA_PATH = "books.dat"; // đường dẫn tới file dữ liệu dùng đọc/ ghi
// Định nghĩa kiểu sách
struct Book {
char maBook[50];
char tenBook[50];
char tacGia[50];
char nhaXB[50];
int namXB;
float donGia;
int soLuong;
float thanhTien;
float thueVAT;
float thucTien;
};
typedef struct Book Book;
// Hàm nhập 1 cuốn sách
Book NhapBook(){
Book book;
cin.ignore();
cout << "Nhap ma book: "; cin.getline(book.maBook, 50);
cout << "Nhap ten book: "; cin.getline(book.tenBook, 50);
cout << "Nhap ten TG: "; cin.getline(book.tacGia, 50);
cout << "Nhap nha XB: "; cin.getline(book.nhaXB, 50);
cout << "Nhap nam XB: "; cin >> book.namXB;
cout << "Nhap don gia: "; cin >> book.donGia;
cout << "Nhap so luong: "; cin >> book.soLuong;
cout << "Nhap thue VAT: "; cin >> book.thueVAT;
book.thanhTien = 0; // chưa tính thì khởi tạo là 0
book.thucTien = 0;
return book;
}
// Hàm nhập n cuốn sách
void NhapBooks(Book b[], int n){
for (int i = 0; i < n; i++){
cout << "Nhap book thu " << i + 1 << ":n";
Book book = NhapBook();
b[i] = book;
cout << "----------------------------n";
}
}
// Hàm in tiêu đề, phục vụ in danh sách dạng bảng
void InTieuDe(){
cout << setw(20) << "Ma Book";
cout << setw(20) << "Ten Book";
cout << setw(20) << "Tac gia";
cout << setw(20) << "Nha XB";
cout << setw(20) << "Nam XB";
cout << setw(20) << "Don gia";
cout << setw(20) << "So luong";
cout << setw(20) << "Thanh tien";
cout << setw(20) << "Thue VAT";
cout << setw(20) <<"Thuc tien" << "n";
}
// hàm xuất thông tin 1 cuốn sách
void XuatBook(Book b){
cout.setf(ios::fixed);
cout << setw(20) << b.maBook;
cout << setw(20) << b.tenBook;
cout << setw(20) << b.tacGia;
cout << setw(20) << b.nhaXB;
cout << setw(20) << b.namXB;
cout << setw(20) << b.donGia;
cout << setw(20) << b.soLuong;
cout << setprecision(2) << setw(20) << b.thanhTien;
cout << setprecision(2) << setw(20) << b.thueVAT;
cout << setprecision(2) << setw(20) << b.thucTien << "n";
}
// Hàm xuất thông tin n cuốn sách
void XuatBooks(Book b[], int n){
// gọi hàm in tiêu đề trước
InTieuDe();
// lặp để in ra thông tin từng cuốn
for(int i = 0; i < n; i++){
XuatBook(b[i]);
}
}
// hàm tính thành tiền cho n cuốn sách
void TinhThanhTien(Book b[], int n){
for(int i = 0; i < n; i++){
b[i].thanhTien = b[i].donGia * b[i].soLuong;
}
}
// hàm tính thực tiền cho n cuốn sách
void TinhThucTien(Book b[], int n){
for(int i = 0; i < n; i++){
b[i].thucTien = b[i].thanhTien * (1 + b[i].thueVAT); // 100% số tiền + VAT * số tiền
}
}
// Hàm sắp xếp giảm dần theo năm XB
void SapXep(Book b[], int n){
for (int i = 0; i < n; i++){
for(int j = i+1; j < n; j++){
// Nếu cuốn trước có năm xuất bản nhỏ hơn cuốn sau thì hoán vị.
// vì j = i + 1 nên j luôn ở sau i
if (b[i].namXB < b[j].namXB){
Book temp = b[i];
b[i] = b[j];
b[j] = temp;
}
}
}
}
// Hàm tìm và in thông tin sách có thực tiền lớn nhất.
void MaxSach(Book b[], int n){
// khởi tạo cuốn đầu tiên là cuốn lớn nhất
int maxTT = b[0].thucTien;
int maxIndex = 0; // lưu chỉ số sách lớn nhất hiện tại
for (int i = 1; i < n; i++){
if (b[i].thucTien > maxTT){
maxTT = b[i].thucTien;
maxIndex = i;
}
}
// in thông tin sách lớn nhất
cout << "Sach co thuc tien lon nhat la:n";
InTieuDe(); // in tiêu đề
XuatBook(b[maxIndex]); // in thông tin sách
}
// Hàm đếm số lượng cuốn sách, tính tổng số lượng
void TongSoCuonSach(Book b[], int n){
int tong = 0;
for(int i = 0; i < n; i++){
tong += b[i].soLuong;
}
cout << "Tong so cuon sach la: " << tong << "n";
}
// Hàm lọc theo thuế VAT, lặp và tìm cách sách có VAT lớn hơn thì in ra
void LocTheoVAT(Book b[], int n){
float value;
cout << "Nhap gia VAT toi thieu: ";
cin >> value;
int count = 0;
for (int i = 0; i < n; i++){
if (b[i].thueVAT > value){
if (count == 0){
// Nếu lần đầu tìm thấy thì in tiêu đề
InTieuDe();
}
XuatBook(b[i]);
count++;
}
}
// Nếu tìm ko được cuốn nào thì báo ko có
if (count == 0){
cout << "Khong tim thay ket qua!n";
}
}
// Hàm ghi các cuốn sách ra file
void toFile(Book b[], int n){
FILE *fptr; // con trỏ file
fptr = fopen(DATA_PATH,"w"); // mở file
if(fptr == NULL) {
printf("Loi mo file!");
exit(EXIT_FAILURE); // thoát chương trình nếu có lỗi mở file
}
fprintf(fptr,"%dn", n); // dòng đầu tiên ghi số cuốn sách
for (int i = 0; i < n; i++){
// một cuốn sách ăn sẽ ghi 8 dòng, không ghi thành tiền & thực tiền vào file
fprintf(fptr, "%sn%sn%sn%sn%dn%fn%dn%fn", b[i].maBook, b[i].tenBook, b[i].tacGia, b[i].nhaXB, b[i].namXB, b[i].donGia, b[i].soLuong, b[i].thueVAT);
}
printf("Ghi %d cuon sach thanh cong tai %s!n", n, DATA_PATH);
fclose(fptr); // đóng file
}
// Hàm đọc các cuốn sách từ file
// n là tham chiếu, vì ta cần thay đổi giá trị của n ở hàm main tại hàm này.
void fromFile(Book b[], int &n){
FILE *fptr;
fptr = fopen(DATA_PATH,"r");
if(fptr == NULL) {
printf("Loi mo file!n");
exit(EXIT_FAILURE); // thoát chương trình nếu có lỗi mở file
}
char tmp[50];
fgets(tmp, 50, fptr); // đọc 1 dòng
n = atoi(tmp); // chuyển chuỗi về số, dòng đầu tiên là số lượng cuốn sách.
// Kiểm tra số món ăn trong file ko đc vượt qua MAX_SIZE, cũng ko được âm
if (n < 0 || n > MAX_SIZE){
printf("So luong cuon sach khong hop le!");
exit(EXIT_FAILURE);
}
for (int i = 0; i < n; i++){
// đọc 8 dòng để lấy thông tin 1 cuốn sách
fgets(b[i].maBook, 50, fptr);
b[i].maBook[strcspn(b[i].maBook, "n")] = 0; // xóa n ở cuối
fgets(b[i].tenBook, 50, fptr);
b[i].tenBook[strcspn(b[i].tenBook, "n")] = 0;
fgets(b[i].tacGia, 50, fptr);
b[i].tacGia[strcspn(b[i].tacGia, "n")] = 0;
fgets(b[i].nhaXB, 50, fptr);
b[i].nhaXB[strcspn(b[i].nhaXB, "n")] = 0;
fgets(tmp, 50, fptr);
b[i].namXB = atoi(tmp);
fgets(tmp, 50, fptr);
b[i].donGia = atof(tmp);
fgets(tmp, 50, fptr);
b[i].soLuong = atoi(tmp);
fgets(tmp, 50, fptr);
b[i].thueVAT = atof(tmp);
b[i].thanhTien = b[i].donGia * b[i].soLuong;
b[i].thucTien = (1 + b[i].thueVAT) * b[i].thanhTien;
}
printf("Doc %d cuon sach tu %s thanh cong!n", n, DATA_PATH);
fclose(fptr);
}
// Hàm in menu
void InMenu(){
cout <<"=================== MENU ======================n";
cout << "1. Nhap sach tu ban phimn";
cout << "2. Hien thi thong tin cac cuon sachn";
cout << "3. Tinh cot thanh tienn";
cout << "4. Tinh cot thuc tienn";
cout << "5. Sap xep giam dan theo nam xbn";
cout << "6. Thong tin sach co thuc tien lon nhatn";
cout << "7. In thong tin tong so cac cuon sachn";
cout << "8. Loc danh sach theo thue VATn";
cout << "9. Luu ra tepn";
cout << "10. Doc tu tepn";
cout << "0. ThoatnLua chon cua ban: ";
}
int main(){
int n = 0, luaChon;
Book books[MAX_SIZE];
while (1){
InMenu();
cin >> luaChon;
switch (luaChon)
{
case 1:
cout << "Nhap so luong book: ";
cin >> n;
if (n <= 0 || n > MAX_SIZE){
cout << "Vui long nhap n trong pham vi 1-100!n";
continue;
}
NhapBooks(books, n);
break;
case 2:
XuatBooks(books, n);
break;
case 3:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
TinhThanhTien(books, n);
break;
case 4:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
if (books[0].thanhTien == 0){
cout << "Vui long tinh thanh tien truoc!";
continue;
}
TinhThucTien(books, n);
break;
case 5:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
SapXep(books, n);
break;
case 6:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
MaxSach(books, n);
break;
case 7:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
TongSoCuonSach(books, n);
break;
case 8:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
LocTheoVAT(books, n);
break;
case 9:
if (n == 0){
cout << "Vui long nhap du lieu truoc!";
continue;
}
toFile(books, n);
break;
case 10:
fromFile(books, n);
XuatBooks(books, n);
break;
case 0:
cout << "Tam biet!n";
exit(0);
default:
cout << "Vui long lua chon cac chuc nang tu 0 - 10!n";
continue;
}
}
}Kết quả chạy chương trình:
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 1
Nhap so luong book: 2
Nhap book thu 1:
Nhap ma book: LT01
Nhap ten book: Lap Trinh Khong Kho
Nhap ten TG: Nguyen Van Hieu
Nhap nha XB: Tu do
Nhap nam XB: 2020
Nhap don gia: 100000
Nhap so luong: 100
Nhap thue VAT: 0.1
----------------------------
Nhap book thu 2:
Nhap ma book: LC01
Nhap ten book: Luyen Code
Nhap ten TG: Nguyen Van Hieu
Nhap nha XB: Tu do
Nhap nam XB: 2021
Nhap don gia: 200000
Nhap so luong: 50
Nhap thue VAT: 0.2
----------------------------
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 2
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LT01 Lap Trinh Khong Kho Nguyen Van Hieu Tu do 2020 100000 100 0 0.1 0
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 0 0.2 0
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 3
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 2
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LT01 Lap Trinh Khong Kho Nguyen Van Hieu Tu do 2020 100000 100 1e+07 0.1 0
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 1e+07 0.2 0
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 4
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 2
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LT01 Lap Trinh Khong Kho Nguyen Van Hieu Tu do 2020 100000 100 1e+07 0.1 1.1e+07
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 1e+07 0.2 1.2e+07
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 5
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 2
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 1e+07 0.2 1.2e+07
LT01 Lap Trinh Khong Kho Nguyen Van Hieu Tu do 2020 100000 100 1e+07 0.1 1.1e+07
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 6
Sach co thuc tien lon nhat la:
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 1e+07 0.2 1.2e+07
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 7
Tong so cuon sach la: 150
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 8
Nhap gia VAT toi thieu: 0.15
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 1e+07 0.2 1.2e+07
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 9
Ghi 2 cuon sach thanh cong tai books.dat!
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 10
Doc 2 cuon sach tu books.dat thanh cong!
Ma Book Ten Book Tac gia Nha XB Nam XB Don gia So luong Thanh tien Thue VAT Thuc tien
LC01 Luyen Code Nguyen Van Hieu Tu do 2021 200000 50 1e+07 0.2 1.2e+07
LT01 Lap Trinh Khong Kho Nguyen Van Hieu Tu do 2020 100000 100 1e+07 0.1 1.1e+07
=================== MENU ======================
1. Nhap sach tu ban phim
2. Hien thi thong tin cac cuon sach
3. Tinh cot thanh tien
4. Tinh cot thuc tien
5. Sap xep giam dan theo nam xb
6. Thong tin sach co thuc tien lon nhat
7. In thong tin tong so cac cuon sach
8. Loc danh sach theo thue VAT
9. Luu ra tep
10. Doc tu tep
0. Thoat
Lua chon cua ban: 0
Tam biet!Qua một số bài tập struct trong C/C+ trên đây, LTKK hi vọng các bạn có thể bổ sung thêm kiến thức về kiểu cấu trúc trong C/C++. Chúc các bạn học tốt!



Để lại một bình luận