zoukankan      html  css  js  c++  java
  • PAT Advanced 1037 Magic Coupon (25) [贪⼼算法]

    题目

    The magic shop in Mars is ofering some magic coupons. Each coupon has an integer N printed on it, meaning that when you use this coupon with a product, you may get N times the value of that product back! What is more, the shop also ofers some bonus product for free. However, if you apply a coupon with a positive N to this bonus product, you will have to pay the shop N times the value of the bonus product… but hey, magically, they have some coupons with negative N’s!
    For example, given a set of coupons {1 2 4 -1}, and a set of product values {7 6 -2 -3} (in Mars dollars M) where a negative value corresponds to a bonus product. You can apply coupon 3 (with N being 4) to product 1 (with value M7) to get M28 back; coupon 2 to product 2 to get M12 back; and coupon 4 to product 4 to get M3 back. On the other hand, if you apply coupon 3 to product 4, you will have to pay M12 to the shop.
    Each coupon and each product may be selected at most once. Your task is to get as much money back as possible.
    Input Specification:
    Each input file contains one test case. For each case, the first line contains the number of coupons NC,followed by a line with NC coupon integers. Then the next line contains the number of products NP,followed by a line with NP product values. Here 1<= NC,NP<=10^5, and it is guaranteed that all the numbers will not exceed 230.
    Output Specification:
    For each test case, simply print in a line the maximum amount of money you can get back.
    Sample Input:
    4
    1 2 4 -1
    4
    7 6 -2 -3
    Sample Output:
    43

    题目分析

    1. 每张卡券上都有一个整数N(N可能是正,也可能是负)
    2. 商品分为两种,一种正整数标记的(记为GP,价值记为VGP),另一种负整数标记的(BP,价值记为VBP)
    3. 卡券(其上数字为N)使用在商品上
      • 使用在普通商品GP上,可获得N*VGP的金额
      • 使用在BP商品上
        • 如果N>0,需支付N*VBP金额
        • 如果N<0,可获得N*VBP金额
    4. 寻找获得最多金币的办法
    5. 每个优惠券和每个产品最多可以被选择一次

    解题思路

    1. 如果要获得最多金币,必须将大正整数N用在大VGP商品上(正正),将小负整数N用在小VBP商品上(负负)
    2. 所有卡券排序(从小到大),所有商品排序(从小到大)
    3. 从左边开始处理卡券和商品均负整数的情况,从右边开始处理卡券和商品均正整数的情况
    4. 0可以不考虑,因为0乘以任何数都为0,不影响结果
    5. 可能有部分优惠券和产品不会被选择

    Code

    Code 01

    #include <iostream>
    #include <algorithm>
    using namespace std;
    int main(int argc, char *argv[]) {
    	int NC,NP;
    	scanf("%d",&NC);
    	int cps[NC]= {0};
    	for(int i=0; i<NC; i++) scanf("%d",&cps[i]);
    	scanf("%d",&NP);
    	int pds[NP]= {0};
    	for(int i=0; i<NP; i++) scanf("%d",&pds[i]);
    	sort(cps,cps+NC);
    	sort(pds,pds+NP);
    	int ans=0;
    	for(int i=0,j=0; i<NC&&j<NP&&cps[i]<0&&pds[j]<0; i++,j++) ans+=(cps[i]*pds[j]);
    	for(int i=NC-1,j=NP-1; i>=0,j>=0&&cps[i]>0&&pds[j]>0; i--,j--) ans+=(cps[i]*pds[j]);
    	printf("%d",ans);
    	return 0;
    }
    
  • 相关阅读:
    BZOJ3670:[NOI2014]动物园(KMP)
    415. [HAOI2009] 旅行
    U10223 Cx大帝远征埃及
    U10206 Cx的治疗
    2741. [济南集训 2017] 掰巧克力
    复习题目汇总 over
    7-20 表达式转换(25 分)
    7-19 求链式线性表的倒数第K项(20 分)(单链表定义与尾插法)
    7-18 银行业务队列简单模拟(25 分)
    7-17 汉诺塔的非递归实现(25 分)(有待改进)
  • 原文地址:https://www.cnblogs.com/houzm/p/12243719.html
Copyright © 2011-2022 走看看