zoukankan      html  css  js  c++  java
  • noip2012 国王游戏

    描述

    恰逢H国国庆,国王邀请n位大臣来玩一个有奖游戏。首先,他让每个大臣在左、右手上面分别写下一个整数,国王自己也在左、右手上各写一个整数。然后,让这n位大臣排成一排,国王站在队伍的最前面。排好队后,所有的大臣都会获得国王奖赏的若干金币,每位大臣获得的金币数分别是:排在该大臣前面的所有人的左手上的数的乘积除以他自己右手上的数,然后向下取整得到的结果。 
    国王不希望某一个大臣获得特别多的奖赏,所以他想请你帮他重新安排一下队伍的顺序,使得获得奖赏最多的大臣,所获奖赏尽可能的少。注意,国王的位置始终在队伍的最前面。

    格式

    输入格式

    第一行包含一个整数n,表示大臣的人数。 
    第二行包含两个整数a和b,之间用一个空格隔开,分别表示国王左手和右手上的整数。接下来n行,每行包含两个整数a和b,之间用一个空格隔开,分别表示每个大臣左手和右手上的整数。

    输出格式

    输出只有一行,包含一个整数,表示重新排列后的队伍中获奖赏最多的大臣所获得的金币数。

    数据

    对于20%的数据,有1≤ n≤ 10,0 < a、b < 8; 
    对于40%的数据,有1≤ n≤20,0 < a、b < 8; 
    对于60%的数据,有1≤ n≤100; 
    对于60%的数据,保证答案不超过10^9; 
    对于100%的数据,有1 ≤ n ≤1,000,0 < a、b < 10000。

    --------------------------------------------------------------------------------

    正解= 贪心+高精.

    贪心证明 :

    设存在 相邻大臣A(l1,r1),B(l2,r2),A,B前左手乘积为Sum :

       当A在B前时: 

            则Ans=max(Sum/r1,Sum*l1/r2) ;

      当B在A前时: 

            则Ans=max(Sum/r2,Sum*l2/r1) ;

      显然 Sum*l2/r1>Sum/r1  ; 

             Sum*l1/r2>Sum/r2 ;

      所以当 Sum*l2/r1>Sum*l1/r2

            即   l2*r2>l1*r1 时  A应在B前

      同理

            即   l2*r2<l1*r1 时  B应在A前

      所以按 l*r 从小到大排序在进行模拟即为正解.

    代码如下:

     1 #include<cstring>
     2 #include<algorithm>
     3 #include<cstdio>
     4 #include<string>
     5 #include<iostream>
     6 #include<queue>
     7 #define INF 99999999
     8 #define LL long long
     9 //using namespace std;
    10 struct STR{
    11     int s[3000];
    12 }ans,sum;
    13 struct P{
    14     int l,r;
    15 }p[1001];
    16 int n;
    17 bool cmp(const P &x,const P &y){
    18     return x.l*x.r<y.l*y.r;
    19 }
    20 void time(STR &a,int b){
    21     int L=a.s[0];
    22     for(int i=1;i<=L;i++) a.s[i]*=b;
    23     for(int i=1;i<=L;i++){
    24         a.s[i+1]+=a.s[i]/10000;
    25         a.s[i]%=10000;
    26     }
    27     while(a.s[L+1]){
    28         ++L;
    29         a.s[L+1]+=a.s[L]/10000;
    30         a.s[L]%=10000;
    31     }
    32     a.s[0]=L;
    33 }
    34 void Max(STR &a,STR b){
    35     if(a.s[0]<b.s[0]) { a=b; return ;}
    36     if(a.s[0]>b.s[0]) return ;
    37     for(int i=a.s[0];i;i--){
    38        if(a.s[i]<b.s[i]) { a=b; return ;}
    39        if(a.s[i]>b.s[i]) return  ;
    40     }
    41 }
    42 STR div(STR a,int b){
    43     int x=0,L=a.s[0];
    44     STR c;
    45     memset(c.s,0,sizeof(c.s));
    46     for(int i=L;i>=1;i--){
    47         x=x*10000+a.s[i];
    48         c.s[i]=x/b;
    49         x%=b;    
    50     }
    51     while(!c.s[L]) --L;
    52     c.s[0]=L;
    53     return c;
    54 }
    55 void put(STR a){
    56     printf("%d",a.s[a.s[0]]);
    57     for(int i=a.s[0]-1;i;i--) printf("%4.4d",a.s[i]);
    58 }
    59 int main(){
    60     freopen("xx.in","r",stdin);
    61     freopen("xx.out","w",stdout);
    62     scanf("%d",&n);
    63     for(int i=0;i<=n;i++) scanf("%d%d",&p[i].l,&p[i].r);
    64     std :: sort(p+1,p+1+n,cmp);
    65     sum.s[0]=sum.s[1]=1;
    66     time(sum,p[0].l);
    67     for(int i=1;i<=n;i++){
    68         Max(ans,div(sum,p[i].r));
    69         time(sum,p[i].l);
    70     }
    71     put(ans); 
    72 }
    View Code
  • 相关阅读:
    javaBean为什么要实现Serializable接口?
    OpenLayers3的WMS空间查询实现多个图层
    (WPS) 网络地理信息处理服务
    window.open跳过浏览器拦截
    linux改权限
    element-ui MessageBox的bug
    element-ui上传文件带token
    MySQL启动出现The server quit without updating PID file错误解决办法
    重装应用商店
    vscode在vue-cli中按照ESlint自动格式化代码
  • 原文地址:https://www.cnblogs.com/Blacko/p/3370433.html
Copyright © 2011-2022 走看看