鱼C论坛

 找回密码
 立即注册
查看: 487|回复: 7

[复制链接]
发表于 2024-9-19 17:10:06 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
.巨人航空公司的飞机由12个座位组成,它每天飞行一个航班,按照下面的功能,写一个座位预定程序:

1)、程序使用一个含12个结构的数组,每个结构要包括一个用于标识座位的编号,一个标识座位是否已经分配出去的标记,座位预订人的姓名和性别。

2)、程序显示并实现以下菜单功能

1、显示所有未被分配的空座位编号

2、显示已经卖出去的座位编号,并能知道乘客姓名以及性别

3、买票,如果没有余票,则提示购票失败

4、退票,将系统已经退票的座位号返还给系统

5、退出系统

提示:

结构体成员     座位编号,座位是否售出标志,乘客姓名,乘客性别

1.)准备工作    给座位编号,标记为未售出

2.)做其他工作   通过枚举类型去做, 按键选菜单功能,选中某一项调用某一个函数

3.)编写功能函数
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2024-9-19 17:13:47 | 显示全部楼层
好的,鱼油,我们可以用C语言来实现这个座位预定程序。让我们一步一步来解决这个问题:

### 第一步:定义结构体来存储座位信息
#include <stdio.h>
#include <string.h>

#define TOTAL_SEATS 12

typedef struct {
    int seat_number;
    int is_sold; // 0表示未售出,1表示已售出
    char name[20];
    char gender[10];
} Seat;

### 第二步:定义函数原型和初始化座位数组

我们需要一些函数来处理不同的功能,比如显示空座位、显示已售座位、预定和退票。
void init_seats(Seat seats[]);
void show_empty_seats(Seat seats[]);
void show_sold_seats(Seat seats[]);
void buy_ticket(Seat seats[]);
void return_ticket(Seat seats[]);
void print_menu();
int get_choice();

定义并初始化座位数组:
void init_seats(Seat seats[]) {
    for (int i = 0; i < TOTAL_SEATS; i++) {
        seats[i].seat_number = i + 1;
        seats[i].is_sold = 0;
        strcpy(seats[i].name, "");
        strcpy(seats[i].gender, "");
    }
}

### 第三步:实现功能函数

1. 显示所有未被分配的空座位编号
void show_empty_seats(Seat seats[]) {
    printf("空座位编号:\n");
    for (int i = 0; i < TOTAL_SEATS; i++) {
        if (seats[i].is_sold == 0) {
            printf("%d ", seats[i].seat_number);
        }
    }
    printf("\n");
}

2. 显示已卖出的座位编号及乘客信息
void show_sold_seats(Seat seats[]) {
    printf("已卖出座位编号及乘客信息:\n");
    for (int i = 0; i < TOTAL_SEATS; i++) {
        if (seats[i].is_sold == 1) {
            printf("座位号: %d, 姓名: %s, 性别: %s\n", seats[i].seat_number, seats[i].name, seats[i].gender);
        }
    }
}

3. 买票功能
void buy_ticket(Seat seats[]) {
    int seat_number;
    printf("输入想要预定的座位号(1-12): ");
    scanf("%d", &seat_number);
    if (seat_number < 1 || seat_number > TOTAL_SEATS || seats[seat_number - 1].is_sold) {
        printf("购票失败!该座位号无效或已售出。\n");
        return;
    }
    printf("输入姓名: ");
    scanf("%s", seats[seat_number - 1].name);
    printf("输入性别: ");
    scanf("%s", seats[seat_number - 1].gender);
    seats[seat_number - 1].is_sold = 1;
    printf("购票成功!\n");
}

4. 退票功能
void return_ticket(Seat seats[]) {
    int seat_number;
    printf("输入想要退的座位号(1-12): ");
    scanf("%d", &seat_number);
    if (seat_number < 1 || seat_number > TOTAL_SEATS || !seats[seat_number - 1].is_sold) {
        printf("退票失败!该座位号无效或未售出。\n");
        return;
    }
    seats[seat_number - 1].is_sold = 0;
    strcpy(seats[seat_number - 1].name, "");
    strcpy(seats[seat_number - 1].gender, "");
    printf("退票成功!\n");
}

### 第四步:打印菜单和获取用户选择
void print_menu() {
    printf("菜单:\n");
    printf("1. 显示所有未被分配的空座位编号\n");
    printf("2. 显示已卖出座位编号及乘客信息\n");
    printf("3. 买票\n");
    printf("4. 退票\n");
    printf("5. 退出系统\n");
    printf("请输入选择(1-5): ");
}

int get_choice() {
    int choice;
    scanf("%d", &choice);
    return choice;
}

### 第五步:主函数来控制整体流程
int main() {
    Seat seats[TOTAL_SEATS];
    init_seats(seats);

    while (1) {
        print_menu();
        int choice = get_choice();
        switch (choice) {
            case 1:
                show_empty_seats(seats);
                break;
            case 2:
                show_sold_seats(seats);
                break;
            case 3:
                buy_ticket(seats);
                break;
            case 4:
                return_ticket(seats);
                break;
            case 5:
                printf("退出系统\n");
                return 0;
            default:
                printf("无效选择,请重新输入。\n");
        }
    }

    return 0;
}

这样,我们就完成了一个简单的座位预定程序。希望这个代码能帮助你理解这个过程。如果有任何问题,请随时提问!

以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2024-9-19 17:17:17 | 显示全部楼层
详细讲解一下代码思路,及代码实现
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2024-9-19 17:17:36 | 显示全部楼层
轻语远歌 发表于 2024-09-19 17:17
详细讲解一下代码思路,及代码实现


好的鱼油,我们来详细讲解一下代码的思路以及具体的实现。

### 1. 代码思路

1. **定义结构体:** 结构体包含座位编号(int)、座位是否已经售出(int)、乘客姓名(char数组)和乘客性别(char)。

2. **初始化座位数组:** 设置座位编号为0到11,所有座位初始状态为未售出,乘客信息为空。

3. **编写函数:**
    - 显示所有未分配的座位编号。
    - 显示已经卖出去的座位编号,显示对应的姓名和性别。
    - 买票操作,查询座位是否已售出,售出时记录乘客信息。
    - 退票操作,将座位状态标记为未售出。
    - 退出系统,程序结束。

4. **菜单功能:** 使用一个循环显示菜单,接受用户输入的选择,根据选择调用相应的函数。

### 2. 代码实现
#include <stdio.h>
#include <string.h>

#define TOTAL_SEATS 12

typedef struct {
    int seatNumber;
    int isSold;
    char name[50];
    char gender;
} Seat;

// 初始化座位
void initializeSeats(Seat seats[]) {
    for (int i = 0; i < TOTAL_SEATS; ++i) {
        seats[i].seatNumber = i + 1;
        seats[i].isSold = 0;
        memset(seats[i].name, 0, sizeof(seats[i].name));
        seats[i].gender = '\0';
    }
}

// 显示所有未分配的空座位编号
void displayAvailableSeats(Seat seats[]) {
    printf("Available seats: \n");
    for (int i = 0; i < TOTAL_SEATS; ++i) {
        if (!seats[i].isSold) {
            printf("Seat %d\n", seats[i].seatNumber);
        }
    }
}

// 显示已经卖出去的座位编号,乘客姓名以及性别
void displaySoldSeats(Seat seats[]) {
    printf("Sold seats: \n");
    for (int i = 0; i < TOTAL_SEATS; ++i) {
        if (seats[i].isSold) {
            printf("Seat %d - Name: %s, Gender: %c\n", seats[i].seatNumber, seats[i].name, seats[i].gender);
        }
    }
}

// 买票
void buyTicket(Seat seats[]) {
    int seatNumber;
    printf("Enter seat number to buy (1-12): ");
    scanf("%d", &seatNumber);

    if (seatNumber < 1 || seatNumber > 12) {
        printf("Invalid seat number!\n");
        return;
    }

    if (seats[seatNumber - 1].isSold) {
        printf("Seat already sold!\n");
    } else {
        printf("Enter your name: ");
        scanf("%s", seats[seatNumber - 1].name);
        printf("Enter your gender (M/F): ");
        scanf(" %c", &seats[seatNumber - 1].gender); // 注意前面有个空格,以处理上一个输入的回车问题
        seats[seatNumber - 1].isSold = 1;
        printf("Ticket bought successfully!\n");
    }
}

// 退票
void cancelTicket(Seat seats[]) {
    int seatNumber;
    printf("Enter seat number to cancel (1-12): ");
    scanf("%d", &seatNumber);

    if (seatNumber < 1 || seatNumber > 12) {
        printf("Invalid seat number!\n");
        return;
    }

    if (!seats[seatNumber - 1].isSold) {
        printf("Seat not sold yet!\n");
    } else {
        seats[seatNumber - 1].isSold = 0;
        memset(seats[seatNumber - 1].name, 0, sizeof(seats[seatNumber - 1].name));
        seats[seatNumber - 1].gender = '\0';
        printf("Ticket canceled successfully!\n");
    }
}

// 显示菜单并获取用户输入
void displayMenu() {
    printf("\nMenu:\n");
    printf("1. Display available seats\n");
    printf("2. Display sold seats\n");
    printf("3. Buy ticket\n");
    printf("4. Cancel ticket\n");
    printf("5. Exit\n");
    printf("Enter your choice: ");
}

int main() {
    Seat seats[TOTAL_SEATS];
    initializeSeats(seats);

    int choice;
    while (1) {
        displayMenu();
        scanf("%d", &choice);

        switch (choice) {
            case 1:
                displayAvailableSeats(seats);
                break;
            case 2:
                displaySoldSeats(seats);
                break;
            case 3:
                buyTicket(seats);
                break;
            case 4:
                cancelTicket(seats);
                break;
            case 5:
                printf("Exiting...\n");
                return 0;
            default:
                printf("Invalid choice!\n");
        }
    }

    return 0;
}

### 3. 代码解释

- **结构体定义:** `Seat` 定义了每个座位包含的属性。
- **初始化函数:** `initializeSeats(Seat seats[])` 初始化每个座位的编号和状态。
- **显示功能:** `displayAvailableSeats()` 和 `displaySoldSeats()` 用于显示座位的状态。
- **预定功能:** `buyTicket()` 用于用户买票,更新座位的状态和乘客信息。
- **退订功能:** `cancelTicket()` 用于用户退票,重置座位的状态和乘客信息。
- **菜单显示和输入选择:** `displayMenu()` 用于显示菜单,主循环读取用户输入并调用相应的功能。

希望这些解释能够帮到您。哪怕您有进一步的问题,欢迎随时提问!

以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2024-9-19 19:18:52 | 显示全部楼层
FishC 发表于 2024-9-19 17:17
好的鱼油,我们来详细讲解一下代码的思路以及具体的实现。

### 1. 代码思路

通过枚举类型去做, 菜单功能和用户输入,
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2024-9-19 19:19:10 | 显示全部楼层
轻语远歌 发表于 2024-09-19 19:18
通过枚举类型去做, 菜单功能和用户输入,


好的,鱼油。我们可以通过枚举类型来管理菜单选项,并结合用户输入来实现功能。以下是详细的步骤和代码实现:

### 1. 定义结构体与枚举类型

首先,我们定义一个结构体来存储座位信息,同时定义一个枚举类型来表示不同的菜单选项。
#include <stdio.h>
#include <string.h>

#define TOTAL_SEATS 12
#define NAME_LENGTH 50

// 结构体定义
typedef struct {
    int seatNumber;
    int isBooked;
    char passengerName[NAME_LENGTH];
    char passengerGender;
} Seat;

// 枚举类型定义
typedef enum {
    SHOW_EMPTY_SEATS = 1,
    SHOW_BOOKED_SEATS,
    BOOK_SEAT,
    CANCEL_SEAT,
    EXIT
} MenuOption;

### 2. 初始化座位

我们可以编写一个函数来初始化所有座位,使它们标记为未售出。
void initializeSeats(Seat seats[], int totalSeats) {
    for (int i = 0; i < totalSeats; i++) {
        seats[i].seatNumber = i + 1;
        seats[i].isBooked = 0; // 0表示未售出
        strcpy(seats[i].passengerName, "");
        seats[i].passengerGender = ' ';
    }
}

### 3. 显示菜单选项

我们用一个简单的函数来显示菜单选项,并从用户那里获取输入。
MenuOption getMenuOption() {
    int option;
    printf("\nMenu:\n");
    printf("1. 显示所有未被分配的空座位编号\n");
    printf("2. 显示已经卖出去的座位编号,并能知道乘客姓名以及性别\n");
    printf("3. 买票\n");
    printf("4. 退票\n");
    printf("5. 退出系统\n");
    printf("请选择一个选项: ");
    scanf("%d", &option);
    return (MenuOption)option;
}

### 4. 显示空座位
void showEmptySeats(Seat seats[], int totalSeats) {
    printf("未被分配的空座位编号:\n");
    for (int i = 0; i < totalSeats; i++) {
        if (!seats[i].isBooked) {
            printf("座位编号: %d\n", seats[i].seatNumber);
        }
    }
}

### 5. 显示已售出座位
void showBookedSeats(Seat seats[], int totalSeats) {
    printf("已经卖出去的座位编号:\n");
    for (int i = 0; i < totalSeats; i++) {
        if (seats[i].isBooked) {
            printf("座位编号: %d, 姓名: %s, 性别: %c\n", seats[i].seatNumber, seats[i].passengerName, seats[i].passengerGender);
        }
    }
}

### 6. 订票
void bookSeat(Seat seats[], int totalSeats) {
    int seatNumber;
    printf("请输入要订的座位编号: ");
    scanf("%d", &seatNumber);

    if (seatNumber <= 0 || seatNumber > totalSeats) {
        printf("座位编号无效\n");
        return;
    }

    if (seats[seatNumber - 1].isBooked) {
        printf("该座位已经被订了\n");
        return;
    }

    seats[seatNumber - 1].isBooked = 1;
    printf("请输入乘客姓名: ");
    scanf("%s", seats[seatNumber - 1].passengerName);
    printf("请输入乘客性别 (M/F): ");
    scanf(" %c", &seats[seatNumber - 1].passengerGender);
    printf("订票成功\n");
}

### 7. 退票
void cancelSeat(Seat seats[], int totalSeats) {
    int seatNumber;
    printf("请输入要退的座位编号: ");
    scanf("%d", &seatNumber);

    if (seatNumber <= 0 || seatNumber > totalSeats) {
        printf("座位编号无效\n");
        return;
    }

    if (!seats[seatNumber - 1].isBooked) {
        printf("该座位未被订\n");
        return;
    }

    seats[seatNumber - 1].isBooked = 0;
    strcpy(seats[seatNumber - 1].passengerName, "");
    seats[seatNumber - 1].passengerGender = ' ';
    printf("退票成功\n");
}

### 8. 主函数处理循环
int main() {
    Seat seats[TOTAL_SEATS];
    initializeSeats(seats, TOTAL_SEATS);

    MenuOption option;
    do {
        option = getMenuOption();
        switch (option) {
            case SHOW_EMPTY_SEATS:
                showEmptySeats(seats, TOTAL_SEATS);
                break;
            case SHOW_BOOKED_SEATS:
                showBookedSeats(seats, TOTAL_SEATS);
                break;
            case BOOK_SEAT:
                bookSeat(seats, TOTAL_SEATS);
                break;
            case CANCEL_SEAT:
                cancelSeat(seats, TOTAL_SEATS);
                break;
            case EXIT:
                printf("退出系统\n");
                break;
            default:
                printf("无效选项,请重新选择\n");
        }
    } while (option != EXIT);

    return 0;
}

这就是整个程序的实现和详细讲解。初始化座位后,程序通过一个循环不断显示菜单,处理用户输入,实现订票、退票和查询功能,直到用户选择退出。

以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2024-9-19 19:35:41 | 显示全部楼层
FishC 发表于 2024-9-19 19:19
好的,鱼油。我们可以通过枚举类型来管理菜单选项,并结合用户输入来实现功能。以下是详细的步骤和代码 ...

// 枚举类型定义
typedef enum {
    SHOW_EMPTY_SEATS = 1,
    SHOW_BOOKED_SEATS,
    BOOK_SEAT,
    CANCEL_SEAT,
    EXIT
} MenuOption;这一段能否具体讲解以下
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2024-9-19 19:35:59 | 显示全部楼层
轻语远歌 发表于 2024-09-19 19:35
// 枚举类型定义
typedef enum {
    SHOW_EMPTY_SE ...


好的,鱼油,我们来看一下嵌套枚举类型定义的具体含义及其作用。

### 枚举类型 `MenuOption`
typedef enum {
    SHOW_EMPTY_SEATS = 1,
    SHOW_BOOKED_SEATS,
    BOOK_SEAT,
    CANCEL_SEAT,
    EXIT
} MenuOption;

### 作用及解释
1. **定义菜单选项枚举类型:**
   `typedef enum { ... } MenuOption;` 是在定义一个枚举类型 `MenuOption`,它包含了一组命名的整数常量。通过使用枚举,我们可以让代码更具可读性。这样我们在处理菜单选项时可以使用这些命名常量,而不仅仅是数字。

2. **枚举值及其意义:**
   - `SHOW_EMPTY_SEATS = 1` 的值为1,表示显示所有未被分配的空座位编号。
   - `SHOW_BOOKED_SEATS` 的值为2(默认从上一个值递增),表示显示已经卖出去的座位编号,并能知道乘客姓名以及性别。
   - `BOOK_SEAT` 的值为3,表示买票。
   - `CANCEL_SEAT` 的值为4,表示退票。
   - `EXIT` 的值为5,表示退出系统。

这样,通过枚举类型不仅可以便于理解和维护代码,还可以防止在代码中直接使用“魔法数字”(magic numbers),提高了代码的可读性和可维护性。

### 代码实现
下面我们将上述结构体定义和枚举类型定义放到程序中,并为每个功能编写函数:
#include <stdio.h>
#include <string.h>

#define TOTAL_SEATS 12

typedef struct {
    int seatNumber;
    int isBooked;
    char name[50];
    char gender;
} Seat;

typedef enum {
    SHOW_EMPTY_SEATS = 1,
    SHOW_BOOKED_SEATS,
    BOOK_SEAT,
    CANCEL_SEAT,
    EXIT
} MenuOption;

void showEmptySeats(Seat seats[], int size) {
    printf("Empty seats: ");
    for (int i = 0; i < size; i++) {
        if (!seats[i].isBooked) {
            printf("%d ", seats[i].seatNumber);
        }
    }
    printf("\n");
}

void showBookedSeats(Seat seats[], int size) {
    printf("Booked seats:\n");
    for (int i = 0; i < size; i++) {
        if (seats[i].isBooked) {
            printf("Seat %d: Name: %s, Gender: %c\n", seats[i].seatNumber, seats[i].name, seats[i].gender);
        }
    }
}

void bookSeat(Seat seats[], int size) {
    int seatNumber;
    printf("Enter seat number to book: ");
    scanf("%d", &seatNumber);

    if (seatNumber < 1 || seatNumber > size || seats[seatNumber - 1].isBooked) {
        printf("Seat not available or already booked.\n");
    } else {
        printf("Enter your name: ");
        scanf("%s", seats[seatNumber - 1].name);
        printf("Enter your gender (M/F): ");
        scanf(" %c", &seats[seatNumber - 1].gender);
        seats[seatNumber - 1].isBooked = 1;
        printf("Seat %d booked successfully.\n", seatNumber);
    }
}

void cancelSeat(Seat seats[], int size) {
    int seatNumber;
    printf("Enter seat number to cancel: ");
    scanf("%d", &seatNumber);

    if (seatNumber < 1 || seatNumber > size || !seats[seatNumber - 1].isBooked) {
        printf("Seat not booked or invalid seat number.\n");
    } else {
        seats[seatNumber - 1].isBooked = 0;
        strcpy(seats[seatNumber - 1].name, "");
        seats[seatNumber - 1].gender = '\0';
        printf("Seat %d cancelled successfully.\n", seatNumber);
    }
}

int main() {
    Seat seats[TOTAL_SEATS];
    for (int i = 0; i < TOTAL_SEATS; i++) {
        seats[i].seatNumber = i + 1;
        seats[i].isBooked = 0;
        strcpy(seats[i].name, "");
        seats[i].gender = '\0';
    }

    while (1) {
        printf("Menu:\n");
        printf("1: Show empty seats\n");
        printf("2: Show booked seats\n");
        printf("3: Book a seat\n");
        printf("4: Cancel a booking\n");
        printf("5: Exit\n");
        printf("Enter an option: ");

        int option;
        scanf("%d", &option);

        switch (option) {
        case SHOW_EMPTY_SEATS:
            showEmptySeats(seats, TOTAL_SEATS);
            break;
        case SHOW_BOOKED_SEATS:
            showBookedSeats(seats, TOTAL_SEATS);
            break;
        case BOOK_SEAT:
            bookSeat(seats, TOTAL_SEATS);
            break;
        case CANCEL_SEAT:
            cancelSeat(seats, TOTAL_SEATS);
            break;
        case EXIT:
            return 0;
        default:
            printf("Invalid option, try again.\n");
        }
    }

    return 0;
}

### 解释
1. **结构体 `Seat`:** 存储座位信息,包括座位编号、是否已预订、乘客姓名和性别。
2. **枚举类型 `MenuOption`:** 定义菜单选项使代码更具可读性。
3. **函数实现:**
   - `showEmptySeats`:显示所有未被预订的座位编号。
   - `showBookedSeats`:显示所有已预订的座位编号及乘客信息。
   - `bookSeat`:预订座位,如果座位已被预订或无效座位编号,则提示错误信息。
   - `cancelSeat`:取消预订,返还该座位的相关信息。
4. **主函数 `main`:** 初始化座位信息,显示菜单并根据用户输入调用不同的功能函数。

通过这种方式,程序更加模块化和可读,用户也能更方便地操作。

以上回复来自 FishC AI 小助理,如未能正确解答您的问题,请继续追问。
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-11-21 19:33

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表