t1001模拟题

题目名称:cs

题目描述:

一年一度的CS联赛开始了,bright义无反顾地加入了比赛。作为一名正直的孩子,bright当然选择了当一名反恐精英。经过若干局的比赛,bright拥有了N元钱(N<=16000)。但是悲剧的是,bright不慎在上一局拆弹时炸弹引爆,英勇就义。所以这一局bright出来时,身上只有一把可怜的小gun。于是bright开始买枪了。你的任务是写一个买枪的程序,统计bright到底买了什么枪。

买枪的方法是这样:

先按下B键,进入购买主菜单;

接下来按一个数字,进入对应的枪械子菜单;

然后再按一个数字,购买对应的枪械或者其他物品(比如防爆盾)。

1买gun:再按1~5 可分别买价格为400500600650750的gun

接下来的描述类似

  2 散弹枪:17003000

  3 微型冲锋枪:1250150017002350

  4 自动步枪:225027503100350042004750

  5 机关枪:5750 (俗称大菠萝)

  6 主武器弹药:50

  7 副武器弹药:25

  8 装备:防弹衣650 防弹衣+头盔1000 闪光弹200 高爆手雷300 烟雾弹300 拆弹装备200 夜视仪1250 防爆盾2200

例如按下B43bright就花了3100块买了他珍爱的M4

特别的是 购买弹药不需按第二个数字,只要按B6B7就行了

简单起见,我们将第x类的第y件武器编号Bxy

其中要注意的是,主武器为菜单中的B2~B5类,副武器是B1类,就是gun,

一开始bright就拥有B12这把警用gun

当买了一把枪,如果bright持有对应的主武器或者副武器,并且持有的枪与购买的枪不同,那么bright会将原来的枪丢去,获得新枪。若持有相同的武器或者钱不够购买新枪则购买失败。

防爆盾属于主武器,拿盾时只能持gun(刀——也算吧),防爆盾不算枪

两种弹药最多各有5份,只能在当前拥有对应的武器时才能购买,若该武器被扔了,子弹也消失。不同的枪要配不同的子弹。

一开始没有弹药,没有枪时购买对应弹药也失败。

高爆手雷,烟雾弹,拆弹装备,夜视仪最多只能持有一个,若重复购买,则购买失败

闪光弹最多拿2

对于防弹衣,没头盔的可以升级为头盔,当然也要花1000元,若是有了头盔的防弹衣再去买普通的防弹衣,购买也失败

钱不够肯定购买失败,失败时钱不变化,当前装备不变化。

输入说明:

第一行:开始拥有的钱N

第二行:一串字符,由若干部分组成,每段开头为一个B,之后有1个或2个数字。bright不会按错键,所以不必考虑错误按键造成的结果。每段之间没有分隔符,所以只有一行。一共不超过100个字符

输出说明:

第一行:一个整数,表示最后剩下了多少钱

第二行:输出主武器的编号,一个空格,及主武器弹药的数量(可为0)。没有主武器则输出empty

第三行:输出副武器的编号,一个空格,及副武器弹药的数量(可为0)。没有副武器则输出empty

第四行:输出剩余的装备,按字典序输出,有几个则输出几个,按字典序排列。中间没有任何分隔符。

输入样例

16000

B14B7B7B7B7B7B7B46B6B6B83B83B84

输出样例

9675

B46 2

B14 5

B83B83B84

View Code
#include <cstdio>
#include <cstdlib>
int cost[9][9];
int tot;
int first[4];
int second[4];
int last[500];
int v[10];
int cmp(const void *a,const void *b){
return (*(int *)a)-(*(int *)b);
}
int main(){
freopen("cs.in","r",stdin);
freopen("cs.out","w",stdout);
scanf("%d\n",&tot);
char c;
char num,l;
cost[1][1]=400;
cost[1][2]=500;
cost[1][3]=600;
cost[1][4]=650;
cost[1][5]=750;
cost[2][1]=1700;
cost[2][2]=3000;
cost[3][1]=1250;
cost[3][2]=1500;
cost[3][3]=1700;
cost[3][4]=2350;
cost[4][1]=2250;
cost[4][2]=2750;
cost[4][3]=3100;
cost[4][4]=3500;
cost[4][5]=4200;
cost[4][6]=4750;
cost[5][1]=5750;
cost[6][1]=50;
cost[7][1]=25;
cost[8][1]=650;
cost[8][2]=1000;
cost[8][3]=200;
cost[8][4]=300;
cost[8][5]=300;
cost[8][6]=200;
cost[8][7]=1250;
cost[8][8]=2200;
first[0]=-1;
second[0]=0;
second[1]=1;
second[2]=2;
last[0]=0;
while ((c=getchar())=='B'){
scanf("%c",&num);
if (num=='6'){
if (first[0]!=-1 && first[3]<5 && tot-50>=0){
first[3]++;
tot-=50;
}
}else
if (num=='7'){
if (second[0]!=-1 && second[3]<5 && tot-25>=0){
second[3]++;
tot-=25;
}
}else
if (num=='1'){
scanf("%c",&l);
int a=num-'0',b=l-'0';
if (b!=second[2] && tot-cost[a][b]>=0){
tot-=cost[a][b];
second[2]=b;
second[3]=0;
}
}else
if (num!='8'){
scanf("%c",&l);
int a=num-'0',b=l-'0';
if ((a!=first[1] || b!=first[2]) && tot-cost[a][b]>=0){
tot-=cost[a][b];
first[0]=0;
first[1]=a;
first[2]=b;
first[3]=0;
}
}else{
scanf("%c",&l);
int a=num-'0',b=l-'0';
if (b==1){
if (!v[1] && !v[2] && tot-cost[a][b]>=0){
tot-=cost[a][b];
v[1]=1;
last[++last[0]]=a*10+b;
}
}else
if (b==2){
if (!v[2] && tot-cost[a][b]>=0){
tot-=cost[a][b];
v[2]=1;
last[++last[0]]=a*10+b;
if (v[1]){
for (int i=1;i<last[0];i++){
if (last[i]==81){
last[i]=last[last[0]];
last[0]--;
}
}
}
}
}else
if (b==3 && tot-cost[a][b]>=0){
if (v[3]<2){
tot-=cost[a][b];
v[3]++;
last[++last[0]]=a*10+b;
}
}else
if (b>=4 && b<=7 && tot-cost[a][b]>=0){
if (!v[b]){
v[b]=1;
tot-=cost[a][b];
last[++last[0]]=a*10+b;
}
}else{
if ((a!=first[1] || b!=first[2]) && tot-cost[a][b]>=0){
tot-=cost[a][b];
first[0]=0;
first[1]=8;
first[2]=8;
first[3]=0;
}
}
}
}
printf("%d\n",tot);
if (first[0]==-1) printf("empty\n");else printf("B%d%d %d\n",first[1],first[2],first[3]);
if (second[0]==-1) printf("empty\n");else printf("B%d%d %d\n",second[1],second[2],second[3]);
qsort(last+1,last[0],sizeof(int),cmp);
for (int i=1;i<=last[0];i++){
putchar('B');
printf("%d",last[i]);
}
putchar('\n');
return 0;
}



 

题目名称:数位游戏cdgame

题目描述:

         Ymqhy正在玩一个数字游戏,其中某人(恩~)暗暗请你帮助她获胜。这个游戏是这样的。一开始有一个数n(1<=n<=1000000),两个人轮流对n进行操作。每次可将n减去它的最大或最小的非零数位。比如3014最大的数位是4,最小的是1,于是它可以减去4或者1,分别产生30103013。直到n变成0时停止,谁将n变为0则获胜。

         根据某种RP因素,游戏都由hy先做。

输入说明:

         第一行是一个整数G(1<=G<=100),表示她们玩了G局游戏;

         接下来G行每行是一个数n

输出说明:

         一共G行,每行输出一串字符。Hy赢了则输出hyymq赢了则输出ymq

输入样例:

2

9

10

输出样例:

hy

ymq


 

View Code
#include <cstdio>
int a[1000001];
int T,n;
int min,max;
int main(){
freopen("cdgame.in","r",stdin);
freopen("cdgame.out","w",stdout);
for (int i=1;i<=1000000;i++){
int t=i;
min=9,max=0;
while (t){
int x=t % 10;
if (x<min && x!=0) min=x;
if (x>max) max=x;
t /= 10;
}
a[i]=!(a[i-min] & a[i-max]);
}
scanf("%d",&T);
for (int i=1;i<=T;i++){
scanf("%d",&n);
if (a[n]) printf("hy\n");else printf("ymq\n");
}
return 0;
}

题目名称:拖拉机tuolaji

题目描述

回忆当年apio,与fishbrightgx三巨牛玩拖拉机的场景还历历在目。其中有一局 gx和我打A,摸牌时都没人亮牌。刚摸完牌时,gx突然说:“我上有个A”。此时bright开始嘀咕了,可能gx不止有一个A吧。可是仍然没有人亮牌。就在要翻底牌的时候,gx将手中的黑桃A亮了出来,此时fish大吼:“啊!你A怎么那么多?”。当时的我很是迷茫,于是想请教您:

         1Gx说手上有1A,那么他手上有不止1A的概率是多少?

         2GX亮出黑桃A后,他手上有不止1A的概率又是多少?

为了描述更清楚些,规定一副牌有n张,gx拿到了m张,黑桃A只有一张,而A一共有K张(和正常的不一样哦)。底牌是归我的,而且gx是不会撒谎的。

输入说明:

一行3个由空格隔开的整数,nmk

输出说明:

输出一行,两个实数,空格隔开,小数点后保留4位。分别为第一个问题和第二个问题的答案

输入样例:

52 13 4

输出样例:

0.3696

0.5612

数据范围

对于

30%的数据n<=30,m<=15

对于100%的数据m<=n<=1,000,000

C++(没写高精度)
 1 #include <cstdio>
2 int n,m,k;
3 double C(int m,int n)
4 { double t=1;
5 for (int i=1;i<=m;i++) t=t*(n-m+i)/i;
6 return t;
7 }
8 int main(){
9 freopen("tuolaji.in","r",stdin);
10 freopen("tuolaji.out","w",stdout);
11 scanf("%d%d%d",&n,&m,&k);
12 double a=k*C(m-1,n-k);
13 double b=C(m,n)-C(m,n-k);
14 printf("%.4lf\n",1-a/b);
15 double c=C(m-1,n-k);
16 double d=C(m-1,n-1);
17 printf("%.4lf\n",1-c/d);
18 return 0;
19 }



 

题目名称:sunglasses

题目描述:

传说中的sunglasses男又在整队了。他站在主席台上,发现只有12班的队伍排的最差。然而你是传说班中的体育委员,在听到sunglasses男的大喝后便不得不整队伍了。传说班队伍中有n个哥,他们站成一排,第i个人分别距离你D_iD_i是整数)。操场的宽度是L。现在你要命令哥们向前或向后移动了。sunglasses男的要求很苛刻,首先n-1个相邻的哥的距离必须尽可能的大,当然他想让距离尽可能得相同。因此任意两个相邻的哥相距必须与(L-1)/(n-1)【使用整数除法】相差最多为1,而且距离为(L-1)/(n-1)(整数除 div)的个数尽可能的多。比如说,当n=4L=8时,可以满足的位置是13581368,但是12471248不可以。

现在你应该如何安排哥们移动,使得队伍满足sunglasses男的要求,并且移动的总步数尽量小。

哥们都必须在整数点移动并且坐标应该大于零(不能撞上你),不大于L(不能出操场)。

输入格式:

1行:2个整数nL

2n+1行:第i+1行表示D_i

输出格式:

一个整数,最小的总步数

输入样例:

5 10

2

8

1

3

9

输出样例:

4

说明:

2<=N<=1500

N<=L<=1,000,000

答案保证不大于1,000,000,000

#include <cstdio>
#include <cstdlib>
#include <cstring>
int f[2][2000];
int a[2000];
int n,l;
int cmp(const void *a,const void *b){
    return *(int *)a-*(int *)b;
}
int min(int a,int b){return a<b?a:b;}
int abs(int a){return a>0?a:-a;}
int main(){
    freopen("sunglasses.in","r",stdin);
    freopen("sunglasses.out","w",stdout);
    scanf("%d%d",&n,&l);
    for (int i=1;i<=n;i++) scanf("%d",&a[i]);
    qsort(a+1,n,sizeof(int),cmp);
    int m=(l-1) / (n-1);
    int p=(l-1) % (n-1);
    int t=0;
    memset(f[1],63,sizeof(f[1]));
    f[1][0]=abs(1-a[1]);
    for (int i=2;i<=n;i++){
        f[t][0]=f[1-t][0]+abs((i-1)*m+1-a[i]);
        for (int j=1;j<=p;j++){
            f[t][j]=min(f[1-t][j],f[1-t][j-1])+abs((i-1)*m+1+j-a[i]);
        }
        t=1-t;
    }
    printf("%d\n",f[1-t][p]);
    return 0;
}