首页 > 试题广场 >

Mooncake (25)

[编程题]Mooncake (25)
  • 热度指数:1701 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 32M,其他语言64M
  • 算法知识视频讲解
Mooncake is a Chinese bakery product traditionally eaten during the Mid-Autumn Festival. Many types of fillings and
crusts can be found in traditional mooncakes according to the region's culture. Now given the inventory amounts and
the prices of all kinds of the mooncakes, together with the maximum total demand of the market, you are supposed to
tell the maximum profit that can be made. Note: partial inventory storage can be taken. The sample shows the following situation: given three kinds of
mooncakes with inventory amounts being 180, 150, and 100 thousand tons, and the prices being 7.5, 7.2, and 4.5
billion yuans. If the market demand can be at most 200 thousand tons, the best we can do is to sell 150 thousand
tons of the second kind of mooncake, and 50 thousand tons of the third kind. Hence the total profit is 7.2 + 4.5/2 =
9.45 (billion yuans).

输入描述:
Each input file contains one test case. For each case, the first line contains 2 positive integers N (<=1000), the number of different kinds 
of mooncakes, and D (<=500 thousand tons), the maximum total demand of the market. Then the second line gives the positive inventory
amounts (in thousand tons), and the third line gives the positive prices (in billion yuans) of N kinds of mooncakes. All the numbers in a
line are separated by a space.


输出描述:
For each test case, print the maximum profit (in billion yuans) in one line, accurate up to 2 decimal places.
示例1

输入

3 20<br/>18 15 10<br/>75 72 45

输出

94.50
n, d = map(int, input().split())
a = list(map(int, input().split()))
p = list(map(float, input().split()))
m = sorted(zip(a,p), key=lambda x: x[1]/x[0] if x[0] else float('Inf'), reverse=True)

ans = 0.0
for x in m:
    if x[0] < d:
        d -= x[0]
        ans += x[1]
    else:
        ans += x[1]/x[0]*d
        break
print('%.2f' % ans)
这里测试样例有陷阱,输入样例中mooncake重量(输入第2行)可能有0。 按照单价(单价=价格/重量)逆序排序,会存在分母为0的情况报错。这种情况,要把重量为0对应的价格加上,得到最终利润。
发表于 2018-05-04 15:28:27 回复(0)
/*库存为0考虑到了,没想到没库存也能收利润,空手套白狼属实牛逼嗷*/
#include <bits/stdc++.h>
using namespace std;
const int AX = 1e3 + 66 ;
struct Node{
	double inv , p ; 
	bool operator < ( const Node &a )const{
		return ( ( p / inv ) - ( a.p / a.inv ) ) > 0 ;
	}
}a[AX];
vector<Node>v;
int main(){
	int n ;
	double d , x ;	
	scanf("%d%lf",&n,&d);
	for( int i = 0 ; i < n ; i++ ){
		scanf("%lf",&a[i].inv);
	}
	for( int i = 0 ; i < n ; i++ ){
		scanf("%lf",&a[i].p);
		if( a[i].inv ) v.push_back(a[i]);
	}
	sort( v.begin() , v.end() );
	double res = 0.0 ; 
	for( int i = 0 ; i < (int)v.size() ; i++ ){
		if( d <= 0 ) break ;
		double tmp = ( ( d >= v[i].inv ) ? v[i].inv : d ) ;
		res += ( tmp / v[i].inv * v[i].p ) ;
		d -= tmp ; 
	}
	for( int i = 0 ; i < n ; i++ ){
		if( !a[i].inv ){
			res += a[i].p ; 
		}
	}
	printf("%.2lf",res);
	return 0 ;
}

发表于 2020-03-01 21:39:30 回复(0)
👿 找了很久的bug: 若月饼数量为0,不是跳过,而是利润直接加上这些月饼的总价。。。(无语)
发表于 2020-02-29 18:41:54 回复(0)
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <algorithm>
#include <cmath>
#include <queue>
#include <iomanip>
using namespace std;

//1070 Mooncake
//坑1,会输入库存为0但是却有price的商品,真是神一般的脑洞。
//坑2,有可能d特别大,到最后都用不完,注意判断队列的empty情况。

struct cake {
    double inventory, tp, mp;
};

cake cakes[1001] = {};

class my_comp {
public:
    bool operator()(const cake& a, const cake& b) {return a.mp < b.mp;}
};
priority_queue < cake, vector<cake>, my_comp> pq;

int main() {
    int n;
    double d;
    double inv, tp, summ=0;
    cin >> n >> d;

    for (int i = 0; i < n; ++i) {
        cin >> inv;
        cakes[i] = { inv,0.0 };
    }

    for (int i = 0; i < n; ++i) {
        cin >> tp;
        if(cakes[i].inventory!=0){
            inv = tp / cakes[i].inventory; //单价,只是借用空间
        }
        else {
            inv = 1e8; //库存为0的,给予最高单价
        }
        cakes[i].tp = tp;
        cakes[i].mp = inv;

        pq.push(cakes[i]);
    }

    cake tmp; 
    while (!pq.empty() && (d>0  || pq.top().inventory==0)){
        tmp = pq.top(); pq.pop();
        if (d > tmp.inventory) {
            d -= tmp.inventory;
            summ += tmp.tp;
        }
        else {
            summ += d*tmp.mp;
            d = 0;
        }
    }
    cout << fixed<<setprecision(2)<< summ;
    return 0;
}
发表于 2019-09-06 16:38:05 回复(0)

/java 有好多过不了pat官网上主要原因是浮点精度用double 剩余的库存也用double
注意他是问平均最高而不是总价格
/

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.Arrays;
import java.util.StringTokenizer;

public class Main {

public static void main(String[] args) throws IOException {
    BufferedReader reader=new BufferedReader(new InputStreamReader(System.in));
    StringTokenizer stringTokenizer,str2;
    stringTokenizer =new StringTokenizer(reader.readLine());
    int N=Integer.parseInt(stringTokenizer.nextToken());
    int D=Integer.parseInt(stringTokenizer.nextToken());
    stringTokenizer =new StringTokenizer(reader.readLine());
    str2=new StringTokenizer(reader.readLine());
    cake [] mokcake =new cake[N];
    for(int i=0;i<N;i++)
    {
        mokcake[i]=new cake();
        mokcake[i].amount=Double.parseDouble(stringTokenizer.nextToken());
        mokcake[i].price=Double.parseDouble(str2.nextToken());
        mokcake[i].ave_price=mokcake[i].price/mokcake[i].amount;
    }
    double count=0f;
    Arrays.sort(mokcake);

    for (int i = 0; i < N; i++) {
        if (D <= 0) break;
        if (D >= mokcake[i].amount) {
            count += mokcake[i].price;
            D-= mokcake[i].amount;
        } else {
            count += D * mokcake[i].ave_price;
            D = 0;
        }
    }
    System.out.printf("%.2f\n",count);
}
public  static class cake implements Comparable<cake>
{
    double amount;
    double price;
    double ave_price;
    public int compareTo(cake p)
    {
        return this.ave_price-p.ave_price>0? -1:1;
    }
}

}

发表于 2018-11-07 18:06:15 回复(0)
import java.util.*;

class MoonCake{
    double price;
    double amount;
    double totalPrice;
    public MoonCake(double price,double amount,double totalPrice){
        this.price=price;
        this.amount=amount;
        this.totalPrice=totalPrice;
    }
}

public class Main{
    public static void main(String[] args){
        Scanner sc=new Scanner(System.in);
        int n=sc.nextInt();
        int d=sc.nextInt();
        ArrayList<MoonCake> cakeList=new ArrayList<MoonCake>();
        for(int i=0;i<n;i++){
            MoonCake moonCake=new MoonCake(0,sc.nextInt(),0);
            cakeList.add(moonCake);
        }
        for(int i=0;i<n;i++){
            double price=sc.nextDouble();
            MoonCake moonCake=cakeList.get(i);
            moonCake.totalPrice=price;
            moonCake.price=price/moonCake.amount;
        }
        Collections.sort(cakeList,new Comparator<MoonCake>(){
            public int compare(MoonCake o1,MoonCake o2){
                if(o1.price>o2.price)
                    return -1;
                else if(o1.price==o2.price)
                    return 0;
                else
                    return 1;
            }
        });
        double totalPrice=0;
        for(int i=0;i<n;i++){
            if(d>cakeList.get(i).amount){
                d-=cakeList.get(i).amount;
                totalPrice+=cakeList.get(i).totalPrice;
            }else{
                totalPrice+=cakeList.get(i).price*d;
                break;
            }
        }
        System.out.printf("%.2f",totalPrice);
    }
}

发表于 2018-10-05 20:07:35 回复(0)
有两个坑🙃:
1. 存在月饼数量为0,但是价格不为0的情况
2. 月饼的重量可能为小数,pat上面有个测试点就是的,牛客网上不存在(不过题目也没说一定是整数,一定要注意😒
发表于 2019-09-07 15:47:25 回复(2)
兄弟们,现在是2021.11.13。测试用例可能已经修改过了,月饼重量可能为小数的问题需要考虑。但是不考虑月饼重量为0也可以全部通过测试用例。PAT和牛客都可以。总重量记得设成double,不能再用int了。
发表于 2021-11-13 17:44:53 回复(0)
当月饼库存为0时,它的价格可以直接加到最大销量里???有点看不懂这种设定。看了评论才整对了答案。
#include <cstdio>
using namespace std;

int main(){
    //B1020 mooncake
    //calculate each cake's price and count for the larger sale profit
    int kinds;
    double amount,sale=0.0;
    scanf("%d%lf",&kinds,&amount);
    
    double* cakeAmount=new double[kinds];
    double* price=new double[kinds];
    double* cakePrice=new double[kinds];
    
    for(int i=0;i<kinds;i++){
        scanf("%lf",cakeAmount+i);
    }
    for(int i=0;i<kinds;i++){
        scanf("%lf",price+i);
        cakePrice[i] = price[i] / cakeAmount[i];
    }
    
    while(amount){
        double max=0.0;
		int maxi=0;
        for(int i=0;i<kinds;i++){
            if(cakePrice[i]>max){
                max=cakePrice[i];
                maxi=i;       
            }
        }
        if(cakeAmount[maxi]>=amount){
            sale += amount*cakePrice[maxi];
            break;
        }
        else{
            sale += cakeAmount[maxi]*cakePrice[maxi];
            amount -= cakeAmount[maxi];
        }
        cakePrice[maxi]=0.0;
    }
    printf("%.2f",sale);
    return 0;
}


发表于 2020-05-13 17:55:13 回复(0)
//!没有遇到前面大神所说得坑鸭,而且我看题目描述也是写的postive鸭,是不是牛客改过了。。。
#include<iostream>
(720)#include<vector>
#include<algorithm>
using namespace std;
struct cake {
	double num;
	double price;
	cake() :num(0), price(0) {}
	cake(double n, double p) :num(n), price(p) {}
};
bool cmp(cake c1, cake c2) {
	return c1.price / c1.num > c2.price / c2.num;
}
int main() {
	int n;
	double needs;
	cin >> n >> needs;
	vector<cake>cakes(n);
	for (int i = 0; i < n; i++) {
		int num;
		cin >> num;
		cakes[i] = cake();
		cakes[i].num = num;
	}
	for (int i = 0; i < n; i++) {
		int price;
		cin >> price;
		cakes[i].price = price;
	}
	sort(cakes.begin(), cakes.end(), cmp);
	double sum = 0;
	for (int i = 0; i <n && needs>0; i++) {
		if (needs >= cakes[i].num) {
			sum += cakes[i].price;
			needs -= cakes[i].num;
		}
		else {
			sum += (cakes[i].price / cakes[i].num) * needs;
			needs = 0;
		}
	}
	printf("%.2lf", sum);
}


发表于 2020-03-28 11:45:39 回复(0)
#include<cstdio>
#include<algorithm>
using namespace std;
struct st{
	float am;
	float p;
};
bool fun(st x1,st x2)
{return x1.p/x1.am>x2.p/x2.am;}
int main()
{
	int n,i,j,a,b;
	float sum=0,d;
	st p0[1001];
	scanf("%d%f",&n,&d);
	for(i=1;i<=n;i++)
		scanf("%f",&p0[i].am);
	for(i=1;i<=n;i++)
		scanf("%f",&p0[i].p);
	sort(p0+1,p0+n+1,fun);
	for(i=1;i<=n;i++)
	{
		if(d<=0)break;
		if(p0[i].am<=d)
		{
			d=d-p0[i].am;
			sum=sum+p0[i].p;
		}
		else {
			sum=sum+p0[i].p*d/p0[i].am;
			break;
		}
	}
	printf("%.2f",sum);
	return 0;
}

发表于 2019-10-07 10:38:50 回复(0)
#include<iostream>
#include<algorithm>
using namespace std;
struct MoonCakes{
    double amounts;
    double price;
    double UnitPrice;
    bool operator < (const MoonCakes& a) const{
        return UnitPrice > a.UnitPrice;
    }   
}M[1001];
int main(void) {
    double D;
    double P = 0,A=0;
    int i,N;
    bool flag = false;
    cin>>N>>D;
    for(i=0; i<N; i++)    cin>>M[i].amounts;
    for(i=0; i<N; i++){
        cin>>M[i].price;
        M[i].UnitPrice = M[i].price / M[i].amounts;        
    }
    sort(M,M+N);
    double temp=0;
    
    for(i=0; i<N; i++){
        if(A+M[i].amounts < D){
            A += M[i].amounts;
            P += M[i].price;
        }
        else{
            temp = D - A;
            P += M[i].UnitPrice * temp;
            break;
        }
    }
    printf("%.2f",P);  
    return 0;
}

发表于 2019-05-30 20:02:33 回复(0)
#include<bits/stdc++.h>
using namespace std;

struct Cake{
    double price,amount,perprice;
};
bool com(Cake c1,Cake c2){ return c1.perprice>c2.perprice;
}

int main(){
    int n,i;
    d,total=0,temp=0;
    Cake cake[1010];
    scanf("%d %lf",&n,&d);
    for(i=0;i<n;i++) scanf("%lf",&cake[i].amount);
    for(i=0;i<n;i++){
        scanf("%lf",&cake[i].price);
        cake[i].perprice=cake[i].price/cake[i].amount;
    }
    sort(cake,cake+n,com);
    for(i=0;i<n;i++){
        if(temp+cake[i].amount<=d){
            total+=cake[i].price;
            temp+=cake[i].amount;
        }else{
            total+=cake[i].perprice*(d-temp);
            temp=d;
        }
        if(temp>=d) break;
    }
    printf("%.2f",total);
    return 0;
}
编辑于 2019-02-08 18:01:25 回复(0)
import sys
n,d = map(int,input().split())
zong = list(map(int,input().split()))
price = list(map(int,input().split()))
for i in range(0,len(zong)):
    zong[i] = [zong[i]]
    zong[i].append(price[i])
    if zong[i][0]!=0:
        zong[i].append(zong[i][1]/zong[i][0])
    else:
        zong[i].append(sys.maxsize)
zong.sort(key=lambda x:(-x[2]))
pri,cur = 0,zong[0][0]
i = 0
while d>cur:
    pri = pri + zong[i][1]
    d = d-cur
    i+=1
    cur = zong[i][0] 
pri = pri+(zong[i][2]*d)
print("%.2f"%pri)

发表于 2018-12-05 16:02:50 回复(0)
N,D=map(int,input().split())
A=list(map(int,input().split()))
B=list(map(int,input().split()))
res,L=0,[]
for i in range(len(A)):
    if A[i]==0:
        res+=B[i]
    else:
        L.append([A[i],B[i]])
L.sort(key=lambda x:-x[1]/x[0])
for e in L:
    res+=min(D,e[0])*(e[1]/e[0])
    D=max(0,D-e[0])
    if not D:
        break
print('{:.2f}'.format(res))

编辑于 2018-09-06 11:04:27 回复(0)

PAT上测试点2说答案错误。不知道为什么。。。

# include <cstdio>
# include <cstdlib>

struct mooncake {
    int inv;
    double price;
    double unitPrice;
} mooncakes[1010];

int N, D;

int compar(const void *a, const void *b) {
    double ans = ((mooncake*)b)->unitPrice - ((mooncake*)a)->unitPrice;
    return (ans > 0 ? 1 : (ans < 0 ? -1 : 0));
}

int main() {
    scanf("%d %d", &N, &D);
    for (int i = 0; i < N; i++) {
        scanf("%d", &(mooncakes[i].inv));
    }
    for (int i = 0; i < N; i++) {
        scanf("%lf", &(mooncakes[i].price));
        mooncakes[i].unitPrice = mooncakes[i].price / mooncakes[i].inv;
    }

    qsort(mooncakes, N, sizeof(mooncake), compar);

    int need = D;
    double profit = 0;
    for (int i = 0; i < N && need > 0; i++) {
        if (need >= mooncakes[i].inv) { //全部卖也不够
            profit += mooncakes[i].price;
            need -= mooncakes[i].inv;
        }
        else { //卖一部分
            profit += need * mooncakes[i].price / mooncakes[i].inv;
            need = 0;
        }
    }

    printf("%.2lf", profit);

    return 0;
}
发表于 2018-03-15 20:20:50 回复(1)
#include <cstdio>
#include <algorithm>
using namespace std;
const int maxn = 1000 + 10;
struct Mooncake{
    int inventory; //庫存量
    int all_price;
    double per_price;
    void init(){
        per_price = (all_price * 1.0) / (inventory * 1.0);
    }
    Mooncake() {}
}cake[maxn];

bool compare(Mooncake m1, Mooncake m2){
    return m1.per_price > m2.per_price;
}

int main(){
    int n, d;
    scanf("%d %d", &n, &d);
    for(int i=0; i<n; i++){
        int num;
        scanf("%d", &num);
        cake[i].inventory = num;
    }
    for(int i=0; i<n; i++){
        int price;
        scanf("%d", &price);
        cake[i].all_price = price;
        cake[i].init();
    }
    sort(cake, cake+n, compare);
    double ans = 0;
    for(int i=0; i<n; i++){
        if(cake[i].inventory < d){
            d -= cake[i].inventory;
            ans += cake[i].all_price;
        }
        else{
            ans += cake[i].per_price * d;
            break;
        }
    }
    printf("%.2f", ans);
    return 0;
}

发表于 2017-09-04 23:54:34 回复(0)
啥头像
填楼

代码如下:
#include <iostream>
#include <vector>
#include <iomanip>
#include <algorithm>

using namespace std;

struct Mooncake
{
    int inventory, price;
    double unitPrice;
    bool operator<(const Mooncake& that) const {
        return (unitPrice > that.unitPrice);
    }
};

int main()
{
    ios::sync_with_stdio(false);
    // 读入数据
    int N, D; cin >> N >> D;
    vector<Mooncake> mooncakes(N);
    for(int i=0; i<N; i++) {
        cin >> mooncakes[i].inventory;
    }
    for(int i=0; i<N; i++) {
        cin >> mooncakes[i].price;
    }
    for(int i=0; i<N; i++) {
        mooncakes[i].unitPrice = (double)mooncakes[i].price/mooncakes[i].inventory;
    }

    // 排序并处理请求
    sort(mooncakes.begin(), mooncakes.end());
    double profit = 0.0;
    for(int i=0; i<N; i++) {
        if(mooncakes[i].inventory <= D) {
            D -= mooncakes[i].inventory;
            profit += mooncakes[i].price;
        } else {
            profit += (mooncakes[i].unitPrice*D);
            break;
        }
    }
    cout << fixed << setprecision(2) << profit << endl;
    return 0;
} 


发表于 2015-12-26 14:04:23 回复(1)