0823模拟赛

由于3道题都做对了,我就懒得写题解了。

一、搭桥

题目描述 Description

有一矩形区域的城市中建筑了若干建筑物,如果某两个单元格有一个点相联系,则它们属于同一座建筑物。现在想在这些建筑物之间搭建一些桥梁,其中桥梁只能沿着矩形的方格的边沿搭建,如下图城市1有5栋建筑物,可以搭建4座桥将建筑物联系起来。城市2有两座建筑物,但不能搭建桥梁将它们连接。城市3只有一座建筑物,城市4有3座建筑物,可以搭建一座桥梁联系两栋建筑物,但不能与第三座建筑物联系在一起。

输入描述 Input Description

在输入的数据中的第一行包含描述城市的两个整数r 和c, 分别代表从北到南、从东到西的城市大小(1 <= r <= 50 and 1 <=  c <= 50). 接下来的r 行, 每一行由c 个(“#”)和(“.”)组成的字符. 每一个字符表示一个单元格。“#”表示建筑物,“.”表示空地。

输出描述 Output Description

在输出的数据中有两行,第一行表示建筑物的数目。第二行输出桥的数目和所有桥的总长度。

样例输入 Sample Input

样例1

3 5

#...#

..#..

#...#

样例2

3 5

##...

.....

....#

样例3

3 5

#.###

#.#.#

###.#

样例4:

3 5

#.#..

.....

....#

样例输出 Sample Output

样例1

5

4 4

样例2

2

0 0

样例3

1

0 0

样例4

3

1 1

AC代码:

#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<ctime>
#include<string>
#include<iostream>
#include<algorithm>
#include<vector>
#include<stack>
#include<queue>
#include<map>
using namespace std;
#define N 100010
#define M 60
#define ll long long
#define xx first
#define yy second
typedef pair<int,int> diy;
inline const int read(){
    register int x=0,f=1;
    register char ch=getchar();
    while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();}
    while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();}
    return x*f;
}
inline const bool in(){
    for(register char ch=getchar();;ch=getchar()) if(ch==‘#‘||ch==‘.‘) return ch==‘#‘;
}
const int dx[]={0,0,1,1,-1,-1,1,-1};
const int dy[]={1,-1,1,-1,1,-1,0,0};
bool mp[M][M];
int fa[N],mark[M][M];
int ans,sum,n,m,cnt;
struct node{
    int x,y,v;
    bool operator < (const node &a) const{
        return v<a.v;
    }
}e[N];
int find(int x){
    return fa[x]==x?x:fa[x]=find(fa[x]);
}
void dfs(int x,int y){
    mark[x][y]=ans;
    for(int i=0,nx,ny;i<8;i++){
        nx=x+dx[i];
        ny=y+dy[i];
        if(mp[nx][ny]&&!mark[nx][ny]){
            dfs(nx,ny);
        }
    }
}
void work1(){
    ans=0;
    for(int i=1;i<=n;i++){
        for(int j=1;j<=m;j++){
            if(mp[i][j]&&!mark[i][j]){
                ans++;
                dfs(i,j);
            }
        }
    }
    printf("%d\n",ans);
}
bool insert(int x1,int y1,int x2,int y2,int v){
    if(x2<1||x2>n||y2<1||y2>m||!mark[x2][y2]) return 1;
    if(mark[x1][y1]==mark[x2][y2]) return 0;
    e[++cnt].x=mark[x1][y1];
    e[cnt].y=mark[x2][y2];
    e[cnt].v=v-1;
    return 1;
}
void build(int x,int y){
    for(int i=x+1;i<=n;i++){
        if(!insert(x,y,i,y,i-x)||!insert(x,y,i,y+1,i-x)||!insert(x,y,i,y-1,i-x)){
            break;
        }
    }
    for(int i=x-1;i;i--){
        if(!insert(x,y,i,y,x-i)||!insert(x,y,i,y+1,x-i)||!insert(x,y,i,y-1,x-i)){
            break;
        }
    }
    for(int i=y+1;i<=m;i++){
        if(!insert(x,y,x,i,i-y)||!insert(x,y,x+1,i,i-y)||!insert(x,y,x-1,i,i-y)){
            break;
        }
    }
    for(int i=y-1;i;i--){
        if(!insert(x,y,x,i,y-i)||!insert(x,y,x+1,i,y-i)||!insert(x,y,x-1,i,y-i)){
            break;
        }
    }
}
void work2(){
    for(int i=1;i<=n;i++){
        for(int j=1;j<=m;j++){
            if(mp[i][j]){
                build(i,j);
            }
        }
    }
    sort(e+1,e+cnt+1);
    for(int i=1;i<=ans;i++) fa[i]=i;
    ans=0;sum=0;
    for(int i=1,fx,fy;i<=cnt;i++){
        fx=find(e[i].x);
        fy=find(e[i].y);
        if(fx!=fy){
            fa[fy]=fx;
            ans++;
            sum+=e[i].v;
        }
    }
    printf("%d %d\n",ans,sum);
}

int main(){
    n=read();m=read();
    for(int i=1;i<=n;i++){
        for(int j=1;j<=m;j++){
            mp[i][j]=in();
        }
    }
    work1();
    work2();
    return 0;
}

二、产生数

题目描述 Description

  给出一个整数 n(n<10^30) 和 k 个变换规则(k<=15)。
  规则:
   一位数可变换成另一个一位数:
   规则的右部不能为零。
  例如:n=234。有规则(k=2):
    2-> 5
    3-> 6
  上面的整数 234 经过变换后可能产生出的整数为(包括原数):
   234
   534
   264
   564
  共 4 种不同的产生数
问题:
  给出一个整数 n 和 k 个规则。
求出:
  经过任意次的变换(0次或多次),能产生出多少个不同整数。
  仅要求输出个数。

输入描述 Input Description

键盘输人,格式为:
   n k
   x1 y1
   x2 y2
   ... ...
   xn yn

输出描述 Output Description

屏幕输出,格式为:
  一个整数(满足条件的个数)

样例输入 Sample Input

   234 2
   2 5
   3 6

样例输出 Sample Output

4

AC代码:

#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<ctime>
#include<string>
#include<iostream>
#include<algorithm>
#include<vector>
#include<stack>
#include<queue>
#include<map>
using namespace std;
#define N 10010
#define M 60
#define ll long long
#define xx first
#define yy second
typedef pair<int,int> diy;
inline const int read(){
    register int x=0,f=1;
    register char ch=getchar();
    while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();}
    while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();}
    return x*f;
}
int num[M],a[M][M];
char s[N];
int f[N],p;
void deal(int x){
    for(int j=1;j<=p;j++){
        f[j]*=x;
    }
    for(int j=1;j<=p<<1;j++){
        if(f[j]>9){
            f[j+1]+=f[j]/10;
            f[j]%=10;
        }
    }
    while(f[p+1]) p++;
}
int main(){
    //freopen("sh.txt","r",stdin);
    int i,j,k,x,y;
    scanf("%s %d",s,&k);
    while(k--) scanf("%d%d",&x,&y),a[x][y]=1;
    for(k=0;k<10;k++){
        for(i=0;i<=10;i++){
            for(j=0;j<10;j++){
                if(i!=j&&i!=k&&j!=k){
                    if(a[i][k]&&a[k][j]){
                        a[i][j]=1;
                    }
                }
            }
        }
    }
    for(i=0;i<10;i++){
        for(j=0;j<10;j++){
            num[i]+=a[i][j];
        }
    }
    f[1]=1;p=1;
    //ll sum=1;
    //for(i=0;i<strlen(s);i++) sum*=(ll)(num[s[i]-‘0‘]+1);
    //cout<<sum;
    for(i=0;i<strlen(s);i++) deal(num[s[i]-‘0‘]+1);
    for(i=p;i;i--) printf("%d",f[i]);
    return 0;
}

三、装箱问题

题目描述 Description

有一个箱子容量为V(正整数,0<=V<=20000),同时有n个物品(0<n<=30),每个物品有一个体积(正整数)。

要求n个物品中,任取若干个装入箱内,使箱子的剩余空间为最小。

输入描述 Input Description

一个整数v,表示箱子容量

一个整数n,表示有n个物品

接下来n个整数,分别表示这n 个物品的各自体积

输出描述 Output Description

一个整数,表示箱子剩余空间。

样例输入 Sample Input

24

6

8

3

12

7

9

7

样例输出 Sample Output

0

AC代码:

#include<cstdio>
#include<iostream>
using namespace std;
#define N 100020
int n,m,c[N],f[N];
int main(){
    scanf("%d%d",&m,&n);
    for(int i=1;i<=n;i++) scanf("%d",&c[i]);
    for(int i=1;i<=n;i++){
        for(int j=m;j>=c[i];j--){
            f[j]=max(f[j],f[j-c[i]]+c[i]);
        }
    }
    printf("%d\n",m-f[m]);
    return 0;
}
时间: 2024-11-03 05:31:49

0823模拟赛的相关文章

【BZOJ】【2741】【FOTILE模拟赛】L

可持久化Trie+分块 神题……Orz zyf & lyd 首先我们先将整个序列搞个前缀异或和,那么某一段的异或和,就变成了两个数的异或和,所以我们就将询问[某个区间中最大的区间异或和]改变成[某个区间中 max(两个数的异或和)] 要是我们能将所有[l,r]的答案都预处理出来,那么我们就可以O(1)回答了:然而我们并不能. 一个常见的折中方案:分块! 这里先假设我们实现了一个神奇的函数ask(l,r,x),可以帮我们求出[l,r]这个区间中的数,与x最大的异或值. 我们不预处理所有的左端点,我

10.30 NFLS-NOIP模拟赛 解题报告

总结:今天去了NOIP模拟赛,其实是几道USACO的经典的题目,第一题和最后一题都有思路,第二题是我一开始写了个spfa,写了一半中途发现应该是矩阵乘法,然后没做完,然后就没有然后了!第二题的暴力都没码QAQ 现在我来写解题报告了,有点饿了QAQ.. 第一题 题目 1: 架设电话线 [Jeffrey Wang, 2007] 最近,Farmer John的奶牛们越来越不满于牛棚里一塌糊涂的电话服务,于 是,她们要求FJ把那些老旧的电话线换成性能更好的新电话线.新的电话线架设 在已有的N(2 <=

bzoj 2741: 【FOTILE模拟赛】L 分塊+可持久化trie

2741: [FOTILE模拟赛]L Time Limit: 15 Sec  Memory Limit: 162 MBSubmit: 1116  Solved: 292[Submit][Status] Description FOTILE得到了一个长为N的序列A,为了拯救地球,他希望知道某些区间内的最大的连续XOR和. 即对于一个询问,你需要求出max(Ai xor Ai+1 xor Ai+2 ... xor Aj),其中l<=i<=j<=r. 为了体现在线操作,对于一个询问(x,y):

9.14 模拟赛

模拟赛第三弹~ T1 题意:给你一个数列,要求删掉任意一种整数,使得剩下的新数列中连续的相等的数最多 例如 2 7 3 7 7 3 3 7 7 5 7,删掉3以后剩的7有四个连续的,最多 思路:暴力枚举去掉哪个......这算是一道水题吧 代码丢了...... TAT T2 题意:有n本书,每本书有宽度和高度.现在你有无数个书架,每个书架的宽度为w,高度由最高的书决定 问在书本按顺序放的情况下,总的书架高度最小是多少 思路:dp,dp[i]表示做到第i本书时的最小高度和. 每次先找到能以编号j的

2014-9-9 NOIP模拟赛

东方幻想乡系列模拟赛Stage 1命题 Nettle审题 Barty ccy1991911 FlanS39 Wagner T2 高精除高精,从来没写过,不知道怎么写,我就用大数减小数ans次,果断超时. T4 Tarjan的板子题,好久没写,中间出现了一些小错误 ①是尽管有双向边,Tarjan函数中也不必排除双向边 ②Tarjan算法有时候不能一步完成,需要做最多n次,用循环解决 ③问题是关于这个题目的虽然输入n代表有n个点,但是下面的连边中有些点根本没出现过,所以设一个数组记录有效点. Pro

【题解】PAT团体程序设计天梯赛 - 模拟赛

由于本人愚笨,最后一题实在无力AC,于是只有前14题的题解Orz 总的来说,这次模拟赛的题目不算难,前14题基本上一眼就有思路,但是某些题写起来确实不太容易,编码复杂度有点高~ L1-1 N个数求和 设计一个分数类,重载加法运算符,注意要约分,用欧几里得算法求个最大公约数即可. 1 #include <cstdio> 2 3 long long abs(long long x) 4 { 5 return x < 0 ? -x : x; 6 } 7 8 long long gcd(long

20161027模拟赛解题报告

20161027模拟赛解题报告 By shenben T1 数学题 模拟即可. 注意开long long T2 技巧题 图片为本题第一张图.(无奈,图传不上来) 首先第一问图中的“Y 字形”的数量,这么简单,在此不细讲. 详见代码 O(n)累加一下就好了 主要说说第二问怎么搞 预处理 每个点分别与其他那些点相连 权值为第1,2,3大(若没有2,3大,就忽略).记录一下权值与对应的点的标号.目的是方便下面的判断. 枚举入度>=3的点,即点B(有多个) 再枚举点B相连的D点(不是点A,C). Ste

[GRYZ]寒假模拟赛

写在前面 这是首次广饶一中的OIERS自编自导,自出自做(zuo)的模拟赛. 鉴于水平气压比较低,机(wei)智(suo)的WMY/XYD/HYXZC就上网FQ下海找了不少水(fei)题,经过他们优(le)美(se)的文字加工后,有故事有题目有人物有奸情的模拟赛正式呈上. 我是正文 题目名 GRYZ娱乐时刻 GRYZ追击时刻 GRYZ就餐时刻 源文件 hyxzc.cpp/c/pas clikar.cpp/c/pas eat.cpp/c/pas 输入文件 hyxzc.in clikar.in ea

【简单思考】noip模拟赛 NTR酋长

NTR酋长 (ntr.pas/.c/.cpp) 黄巨大终于如愿以偿的进入了czy的后宫中……但是czy很生气……他要在黄巨大走到他面前的必经之路上放上几个NTR酋长来阻挡黄巨大. 众所周知,NTR酋长有一个技能是沟壑(F).它会在地图上产生一条长长的障碍物阻挡人前进.Czy打算在一个n*m的矩形(必经之路?)中放上NTR酋长.NTR酋长要一个一个放下去,而且每放一个都会向四角倾斜的方向放出无限长的沟壑,而已经被沟壑挡住的地方就不能再放NTR酋长了. 请注意:不会出现沟壑的路径挡住另一个沟壑的情况