标题:新年好,请指教,谢谢。
只看楼主
清微御宇
Rank: 6Rank: 6
来 自:开封
等 级:侠之大者
威 望:2
帖 子:318
专家分:497
注 册:2012-1-15
得分:2 
回复 12楼 心灯甚亮
这个偶的vc6.0编译.c文件通不过,定义变量需要在块的开头,
然后.cpp文件还是木有通过,
system无法解析,偶这编译器无语了,加了头文件才是出来了,终于可以看到效果了,学习下!

Stay hungry , Stay foolish!
2013-02-11 22:16
TonyDeng
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:贵宾
威 望:304
帖 子:25859
专家分:48889
注 册:2011-6-22
得分:0 
程序代码:
/*
要为一个餐厅做顾客点餐和买单的程序,要求要用函数、循环和指针。具体步骤是:
1 输入选项:食物有 fish($3), chips($2), hamburgers($3), cheese($4)(顾客只有点了hamburgers时才询问),饮料有
  三种soft drinks($1), coffee/tea($1),税率为5%;
2 输出价钱选项有:total food(食物),total drink (饮料),total order(订餐总价),tax(税)、total owing(应收)、
  Amount tendered(收钱),change(找零)。
*/

#include <stdio.h>
#include "utility.h"

// 食品数据结构
struct food_t
{
    int id;                // 编码
    char name[20];        // 名称
    double price;        // 价格
    int bound;            // 捆绑食品的编码
    bool enabled;        // 可用性
};

// 饮料数据结构
struct drink_t
{
    int id;                // 编码
    char name[20];        // 名称
    double price;        // 价格
};

// 订单数据结构
struct order_t
{
    int type;            // 品类编码: 0-食品 1-饮料
    int id;                // 物品编码
    int quantity;        // 数量
};

static food_t foods[4] = {
    { 1, "fish", 3.0, 0, true },
    { 2, "chips", 2.0, 0, true },
    { 3, "hamburgers", 3.0, 0, true },
    { 4, "cheese", 4.0, 3, false }
};
static const drink_t drinks[3] = {
    { 1, "soft drinks", 1.0 },
    { 2, "coffee", 1.0 },
    { 3, "tea", 1.0 }
};
static const double tax_rate = 0.05;        // 税率
static order_t order_list[10];                // 购物清单,每单不超过10项
static int order_index = 0;                    // 购物当前序数

void initialization(void);
int order_menu(const int type);
void check_bound(void);
void order(const int type, const int id);
void display_account(void);
void account(void);

// 程序主入口
int main(void)
{
    int choice;
    do
    {
        cls();
        display_account();
        printf_s("[1] food\n");
        printf_s("[2] drink\n");
        printf_s("[3] account\n");
        printf_s("[0] exit\n");
        printf_s("Choice: ");
        choice = gets_int(1);
        switch (choice)
        {
            case 1:
            case 2:
                order_menu(choice - 1);
                break;
            case 3:
                account();
                break;
            default:
                break;
        }
    } while (choice != 0);

    return 0;
}

// 初始化系统
void initialization(void)
{
    // 复位订单项目计数器
    order_index = 0;

    // 恢复原始菜单,没有绑定项的食品,初始时不显示
    for (int index = 0; index < sizeof(foods) / sizeof(food_t); ++index)
    {
        if (foods[index].bound > 0)
        {
            foods[index].enabled = false;
        }
    }
}

// 物品选择菜单
int order_menu(const int type)
{
    int choice;
    do
    {
        cls();
        display_account();
        int index;
        switch (type)
        {
            case 0:
                for (index = 0; (index < sizeof(foods) / sizeof(food_t)) && foods[index].enabled; ++index)
                {
                    printf_s("[%2d] %-20s $%-10.2f\n", foods[index].id, foods[index].name, foods[index].price);
                }
                break;
            case 1:
                for (index = 0; index < sizeof(drinks) / sizeof(drink_t); ++index)
                {
                    printf_s("[%2d] %-20s $%-10.2f\n", drinks[index].id, drinks[index].name, drinks[index].price);
                }
                break;
            default:
                break;
        }
        printf_s("[ 0] return\n");
        printf_s("Choice: ");
        choice = gets_int((index % 10) + 1);
        if ((choice > 0) && (choice <= index))
        {
            order(type, choice);
            if (type == 0)
            {
                check_bound();
            }
        }
    } while (choice != 0);

    return choice;
}

// 检查绑定食品
void check_bound(void)
{
    for (int i = 0; i < sizeof(foods) / sizeof(food_t); ++i)
    {
        if (foods[i].bound > 0)
        {
            for (int index = 0; index < order_index; ++index)
            {
                if ((order_list[index].type == 0) && (order_list[index].id == foods[i].bound))
                {
                    foods[i].enabled = true;
                }
            }
        }
    }
}

// 输入物品数量,数量为零时取消当前物品
void order(const int type, const int id)
{
    int quantity;

    putchar('\n');
    printf_s("%-20s\n", (type == 0) ? foods[id - 1].name : drinks[id - 1].name);
    do
    {
        printf_s("Please input quantity: ");
    } while ((quantity = gets_int(4)) < 0);
    if (quantity > 0)
    {
        order_list[order_index].type = type;
        order_list[order_index].id = id;
        order_list[order_index].quantity = quantity;
        ++order_index;
    }
}

// 显示购物清单
void display_account(void)
{
    for (int index = 0; index < order_index; ++index)
    {
        const char* name = (order_list[index].type == 0) ? foods[order_list[index].id - 1].name : drinks[order_list[index].id - 1].name;
        double price = (order_list[index].type == 0) ? foods[order_list[index].id - 1].price : drinks[order_list[index].id - 1].price;
        int quantity = order_list[index].quantity;
        printf_s("%02d. %-20s $%-10.2f %4d $%-10.2f \n", index + 1, name, price, quantity, price * quantity);
    }
    printf_s("\n\n");
}

// 结算
void account(void)
{
    cls();
    display_account();

    double total_food = 0.0;
    double total_drink = 0.0;
    for (int index = 0; index < order_index; ++index)
    {
        switch (order_list[index].type)
        {
            case 0:
                total_food += foods[order_list[index].id - 1].price * order_list[index].quantity;
                break;
            case 1:
                total_drink += drinks[order_list[index].id - 1].price * order_list[index].quantity;
                break;
            default:
                break;
        }
    }
    double total_order = total_food + total_drink;
    double tax = total_order * tax_rate;
    double total_owing = total_order + tax;

    printf_s(" Total food: $%.2f\n", total_food);
    printf_s("Total drink: $%.2f\n", total_drink);
    printf_s("Total order: $%.2f\n", total_order);
    printf_s("        Tax: $%.2f\n", tax);
    printf_s("Total owing: $%.2f\n", total_owing);

    putchar('\n');
    printf_s("Now account? (Y/N)");
    if (get_bool())
    {
        double amount_tendered;
        do
        {
            printf_s("Input amount tendered: ");
            amount_tendered = gets_double(20);
        } while (amount_tendered < total_owing);
        putchar('\n');
        printf_s("Amount tendered: $%.2f\n", amount_tendered);
        printf_s("         Change: $%.2f\n", amount_tendered - total_owing);
        Pause();
        initialization();
    }
}

utility.h
程序代码:
#ifndef _UTILTITY
#define _UTILTITY

// 清空控制台屏幕
void cls(void);

// 暂停程序
void Pause(void);

// 从控制台读入指定位数的整数,可含负号
int gets_int(const int length);

// 从控制台读入指定位数的浮点数,可含负号
double gets_double(const int length);

// 从控制台读入逻辑值,只接受y/n形式的输入
bool get_bool(void);

#endif

utility.cpp的代码就不贴了,黏贴回去编译不了的,不要说不行,自己写剩下的那些吧。

[ 本帖最后由 TonyDeng 于 2013-2-11 23:38 编辑 ]

授人以渔,不授人以鱼。
2013-02-11 22:56
新手求收
Rank: 1
等 级:新手上路
帖 子:2
专家分:2
注 册:2013-2-14
得分:2 
啊 好多英文啊!
2013-02-14 13:57
Susake
Rank: 15Rank: 15Rank: 15Rank: 15Rank: 15
来 自:女儿国的隔壁
等 级:贵宾
威 望:23
帖 子:2288
专家分:6481
注 册:2012-12-14
得分:0 
原来版主在忙这个啊

仰望星空...........不忘初心!
2013-02-14 13:59
清微御宇
Rank: 6Rank: 6
来 自:开封
等 级:侠之大者
威 望:2
帖 子:318
专家分:497
注 册:2012-1-15
得分:0 
回复 32楼 TonyDeng
今天终于把学习完了,想过用结构体,但肯更不会用绑定食物编码和可用性来关联汉堡和奶酪,在取得食物饮料种类时也很给力,在增加食物等品种时,基本不要玩什么改动…………,第二次看大牛贴代码学习了!顺便问几问题?
1.为啥输入都用包装方法难道在里面加判断和输入次数,保证输入的可靠性?
2.结构体称为数据结构,看数据结构里c实现的一些代码如抽象数据类型线性表的实现它们管哪里的结构体叫存储结构,数据结构是研究什么的,实现那些抽象数据类型的数据结构有什么意义?

Stay hungry , Stay foolish!
2013-02-17 12:49
TonyDeng
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:贵宾
威 望:304
帖 子:25859
专家分:48889
注 册:2011-6-22
得分:0 
1.那些输入方法,是过滤掉非法字符后得到的数据。我们知道,C的流输入函数,只有在按下Enter键之后才开始处理,在重新进入程序流程之前,我们是无法预料用户在键盘上敲什么的,这个时候只有把用户的所有输入(从开始按键直到按下Enter键之间)都接收进来,防止堵塞流程(所有scanf()无法读入的数据都会留在输入缓冲区中),再慢慢整理得到合法的数据。这是当时为了兼容ANSI C标准库函数而设计的封装,没有使用平台特性的即时检测按键函数,关键是按下Enter才能处理这个很要命。这些封装函数,类似如你输入"123abc456",它会在舍弃掉非法的abc,根据指定的位数,提取出相应的整数,不会出错,即使是全部按键均是无效字符或者直接按下Enter键,它也返回零——用于常见的不输入按回车取默认值操作。

2.我这里说的“数据结构”,只是“数据的结构”,亦即数据库中的表结构概念,根据每个字段的性质和定义,自己可以想像得到用法。

授人以渔,不授人以鱼。
2013-02-17 13:14
TonyDeng
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:贵宾
威 望:304
帖 子:25859
专家分:48889
注 册:2011-6-22
得分:0 
通常说的数据结构课程中的数据结构,是指对应于某种特定的数据处理手法而设计的数据组织形式,数据的结构和操纵这种数据包的手法,统一起来形成数据结构课程。比如链表,这是一种为了方便插入和删除而设计的数据处理方法,适用于无法预先获得连续空间、或需要动态分配空间(其实动态的本质就是无法连续)的情况下使用类似数组的方式处理数据,数组是一支硬杆,所有数据紧密排布在一起,每个数据格的位置是相对固定的,可以用简单的算术计算出来,但链表是一串念珠,每颗珠子之间的连接用松软的绳子连接起来,珠子之间的相对位置不固定(绝对空间也不固定),珠子与珠子之间是通过指针指示器指出下一个或前一个珠子在哪里来寻找的,这种锁链式结构,就决定了链表只能从某个珠子开始顺着次序沿指针一路追寻下去直到指定的珠子为止,无法像数组那样通过简单的算术一步到位,但插入和删除珠子,却比硬杆容易得多。根据这样的性质,你再看链表是如何设计结构体的就知道了,它无非是两个关键因素,一是数据本身(所谓数据本身,既可以是基本的数据类型,也可以是复杂的结构体,甚至是对象),二是指针指示器用于指出下一个或上一个数据点在哪里,只有一个指示器的叫单向链表,两个指示器的是双向链表,为了获得有效的指针,所以凡是构造链表,都要先得到下一个珠子的储存地址,才能给前面的珠子的指针指示器赋值,这就是那种构造算法的关键原理。所谓数据结构课程,无非是学习这样一些数据的处理手法而已,其实知道了原理,自己想也可以想得出来该怎么设计结构体和相应的处理算法,甚至可以自己构造更合适的数据结构——课程上的数据结构不是包打天下的,要根据现实情况变化,课程只是教给你一种思想罢了。

授人以渔,不授人以鱼。
2013-02-17 13:37
TonyDeng
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
等 级:贵宾
威 望:304
帖 子:25859
专家分:48889
注 册:2011-6-22
得分:0 
以下是引用清微御宇在2013-2-17 12:49:05的发言:

想过用结构体,但肯更不会用绑定食物编码和可用性来关联汉堡和奶酪,在取得食物饮料种类时也很给力,在增加食物等品种时,基本不要玩什么改动…………,

这种叫“表驱动法”。那些内化的数组,可以外置到外部文件中,程序启动时再读入,那样增减变化食品时连程序都不用改。

授人以渔,不授人以鱼。
2013-02-17 14:36
清微御宇
Rank: 6Rank: 6
来 自:开封
等 级:侠之大者
威 望:2
帖 子:318
专家分:497
注 册:2012-1-15
得分:0 
回复 38楼 TonyDeng
学习了,谢谢版版的精彩回答!

Stay hungry , Stay foolish!
2013-02-17 15:08



参与讨论请移步原网站贴子:https://bbs.bccn.net/thread-398467-1-1.html




关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.142099 second(s), 7 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved