题目要求:
1、用户在购置网站上有消费积分m,最近网站推出积分换购的活动。换购商品的【种类数是不确定的】,
如:“李宁双肩包”下架了,但又增加了“香皂”、“牙刷”等。
2、每种商品换购的次数不限,如:换购“新款毛巾”10条、12条、100条,都可以。
3、用户积分换购后几乎都会有剩余,找出换购后积分损失最小的前5种组合。
#include <stdio.h>
#define N 10 //添加商品信息时,只需添加后,更改N的值
#结构体的嵌套
struct stru_goods {
char name[40];//表示商品的名称。
float price;//表示商品的单价。
int num_now = 0; //买的当前数,初始值为0
int num_max = 0; //能买的最大数,先初始化为0
};
struct stru_goods goods[N] = {
{"李宁双肩包", 8200},
{"新款毛巾", 678},
{"金吉星软包抽纸", 1040},
{"2018洗车大毛巾", 1250},
{"小米 移动电源2", 7900},
{"不锈钢保温杯", 8690},
{"滋润型护肤脂", 710},
{"真好芦荟胶", 1900},
{"维达 手帕纸", 2090},
{"佳洁士巨人专用", 395}
};
struct stru_choice { //结构体的嵌套
struct stru_goods goods_[N] = {
{"李宁双肩包", 8200},
{"新款毛巾", 678},
{"金吉星软包抽纸", 1040},
{"2018洗车大毛巾", 1250},
{"小米 移动电源2", 7900},
{"不锈钢保温杯", 8690},
{"滋润型护肤脂", 710},
{"真好芦荟胶", 1900},
{"维达 手帕纸", 2090},
{"佳洁士巨人专用", 395}
};//每种选择的每种商品的基本选择情况//先初始化不变的值,即名称和单价
float consum_credits = 0.0; //每种选择所消耗的积分,初始值为0
};
struct stru_choice choices[5];//定义一个只存储五种选择的结构体
定义一个choices结构体数组:放置5个最佳选择
#循环的递归
void deal_goods(int i) { //递归 用于列举出所有可行的搭配 多次调用sum_goods
struct stru_goods *p;
p = &goods[i];//每次所指的元素不同
if (i < N) {
for (p->num_now = 0; p->num_now <= p->num_max; p->num_now++) { //now在变化
deal_goods(i + 1);
}
} else
sum_goods();
}
#主要部分
void sum_goods() { //计算各搭配所用的积分,存入结构体chioces数组,以大换小
float sum_credits = 0.0;
struct stru_goods *p;
p = goods;
struct stru_choice *tp;//choice结构体数组指针
///中间变量 用于存储所有选择的各个商品购买数量 下一步:有用—进一步存入sp所指的替换值 无用—第二个sum_goods()中清零
struct stru_choice *fp;
struct stru_choice c[1];
fp = c;
//
struct stru_choice *sp;//sp 指向min的指针
int k = 0;
while (p < goods + N) {
sum_credits = sum_credits + p->num_now * p->price;//累加得到现在方案 消耗的积分
fp->goods_[k].num_now =
p->num_now;//将此时的购买数 存入中间变量 下一步:如果有用—进一步存入sp所指的替换值 无用—第二个sum_goods()中清零
k++;
p++;
}
if (sum_credits <= credits) {//每次都找出最小值
float min = choices[0].consum_credits;
for (tp = choices; tp < (choices + 5); tp++) {
if (tp->consum_credits <= min) {
min = tp->consum_credits;
sp = tp;//sp指向此时的tp所指的最小值
}
}
if (sum_credits > min) {//若此时的积分大于最小值—替换、、最终choices数组中为5个消耗积分最多的方案 但还没有排序
sp->consum_credits = sum_credits;
for (int k = 0; k < N; k++) {
sp->goods_[k].num_now = fp->goods_[k].num_now;//商品购买数替换
}
}
}
}
#显示
void print() {
struct stru_choice *tp;
int n = 1;
//中间变量
struct stru_choice s[1];
struct stru_choice *sp;
sp = s;
冒泡法 排序 替换信息
for (int i = 0; i < 5; i++) {
for (int j = 0; j < 5 - i; j++) {
for (tp = choices; tp < choices + 5; tp++) {
if (tp->consum_credits <= (tp + 1)->consum_credits) {
*sp = *tp;
*tp = *(tp + 1);
*(tp + 1) = *sp;
}
}
}
}
/输出/
printf("以下为积分损失最小的5种换购方案:\n\n");
for (tp = choices; tp < (choices + 5); tp++) {
printf("#—————第%d选择———————————#\n以下商品消耗积分:%0.0f\n商品名称 需积分 换购数量\n—————————————————————\n",
n, tp->consum_credits);
for (int k = 0; k < N; k++) {
printf("%-15s %-10.0f %-2d\n", tp->goods_[k].name, tp->goods_[k].price, tp->goods_[k].num_now);
}
n++;
printf("========================================\n\n");
}
}
#功能测试
int main() {
int i;//商品序号
printf("请输入您所有的积分:");
scanf("%f", &credits);
printf("\n===================================\n 您的总积分有%0.0f\n===================================\n\n",
credits);
struct stru_goods *p;
for (p = goods; p < (goods + N); p++) {
p->num_max = credits / p->price; //计算可购买的最大数
}
deal_goods(0);//函数实现
print();//显示前五种方案
return 0;
}
#示例
请输入您所有的积分:5093 =================================== 您的总积分有5093 =================================== 以下为积分损失最小的5种换购方案: #—————第1选择———————————# 以下商品消耗积分:5091 商品名称 需积分 换购数量 ————————————————————— 李宁双肩包 8200 0 新款毛巾 678 2 金吉星软包抽纸 1040 0 2018洗车大毛巾 1250 1 小米 移动电源2 7900 0 不锈钢保温杯 8690 0 滋润型护肤脂 710 0 真好芦荟胶 1900 0 维达 手帕纸 2090 1 佳洁士巨人专用 395 1 ======================================== #—————第2选择———————————# 以下商品消耗积分:5090 商品名称 需积分 换购数量 ————————————————————— 李宁双肩包 8200 0 新款毛巾 678 0 金吉星软包抽纸 1040 0 2018洗车大毛巾 1250 0 小米 移动电源2 7900 0 不锈钢保温杯 8690 0 滋润型护肤脂 710 2 真好芦荟胶 1900 0 维达 手帕纸 2090 1 佳洁士巨人专用 395 4 ======================================== #—————第3选择———————————# 以下商品消耗积分:5090 商品名称 需积分 换购数量 ————————————————————— 李宁双肩包 8200 0 新款毛巾 678 0 金吉星软包抽纸 1040 1 2018洗车大毛巾 1250 1 小米 移动电源2 7900 0 不锈钢保温杯 8690 0 滋润型护肤脂 710 1 真好芦荟胶 1900 0 维达 手帕纸 2090 1 佳洁士巨人专用 395 0 ======================================== #—————第4选择———————————# 以下商品消耗积分:5088 商品名称 需积分 换购数量 ————————————————————— 李宁双肩包 8200 0 新款毛巾 678 1 金吉星软包抽纸 1040 0 2018洗车大毛巾 1250 1 小米 移动电源2 7900 0 不锈钢保温杯 8690 0 滋润型护肤脂 710 0 真好芦荟胶 1900 0 维达 手帕纸 2090 0 佳洁士巨人专用 395 8 ======================================== #—————第5选择———————————# 以下商品消耗积分:5086 商品名称 需积分 换购数量 ————————————————————— 李宁双肩包 8200 0 新款毛巾 678 2 金吉星软包抽纸 1040 1 2018洗车大毛巾 1250 0 小米 移动电源2 7900 0 不锈钢保温杯 8690 0 滋润型护肤脂 710 0 真好芦荟胶 1900 1 维达 手帕纸 2090 0 佳洁士巨人专用 395 2 ======================================== -------------------------------- Process exited after 3.644 seconds with return value 0 请按任意键继续. . .