第三次校赛链接:戳我

1001

考虑前半组数,我们只需要标记每个数出现的次数,再加上这个数之前的数出现的次数,即为这个数在m次操作中总共需要翻转的次数(即求前缀和),再根据翻转的奇偶性判断最后这个位置上的数有没有翻转即可。后半组数的处理方法类似。

 #include<cstdio>
#include<iostream>
#include<cstring>
#include<string>
#include<cmath>
#include<algorithm>
#include<string>
#include<vector>
using namespace std;
int s[];
int m,n,vis[]={},d[]={};
int main()
{ while(scanf("%d%d",&n,&m)!=EOF)
{
memset(vis,,sizeof(vis));
for(int i=;i<n;i++)
        scanf("%d",&s[i]);
for(int i=;i<m;i++)
{
scanf("%d",&d[i]);
}
sort(d,d+m);
for(int i=;i<m;i++)
{
vis[d[i]-]++;
vis[n-d[i]]++;
}
for(int i=;i<n/;i++)
{
vis[i]+=vis[i-];
vis[n-i-]+=vis[n-i];
}
for(int i=;i<n;i++)
{
        if(i>)
            printf(" ");
if(vis[i]%==)
printf("%d",s[i]);
else
printf("%d",s[n-i-]);
}
printf("\n");
}
return ;
}

1002

很明显环中的最大值为a与b的最小公倍数,最小值为最大公因数。需要理论证明的同学请私戳学长。

 #include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
#define ll long long
using namespace std;
ll Gcd(ll a,ll b)
{
    return b?Gcd(b,a%b):a;
}
int main()
{
    ll a,b;
    while(scanf("%lld %lld",&a,&b)!=EOF)
    {
        ll gcd=Gcd(a,b);
        ll lcm=a/gcd*b;
        printf("%lld\n",lcm-gcd);
    }
    return ;
}

1003

对于一个n*n的棋盘,我们分两种情况讨论:
第一种情况,n是一个奇数。那么这种时候,棋盘有一个中心点,且总格子数为偶数。
第二种情况,n是一个偶数。那么这种时候,棋盘没有中心点,且总格子数为偶数。

当n为偶数时,无论先手如何行动,后手只要保持与其 关于棋盘中心对称 放子,那么就已经是后手的必胜态。具体说明如下:
马的攻击范围,是与马成3*2或2*3的矩形的 与马对称的顶点。设n*n棋盘上每个格子坐标依次为(1,1)(1,2)…(n,n),倘若先手选择把棋子放置在(i,j)格上,那么后手相对称的放置方法为,放置在(n+1-i,n+1-j)上。现在我们来证明后手总是可 以在(n+1-i,n+1-j)上落子。

因为格子的坐标都是整数,所以不可能存在先手放置在(i,j)的马能吃到(n+1-i,n+1-j)的情况。又因为开局时棋盘是关于中心对称的,而每一回合后手总是跟随先手对称落子,所以每回合棋盘的各个格子的状态必然是关于棋盘 中心对称的。

所以易知,当先手能够把棋子放置在(i,j)格上的时候,后手总是可以在(n+1-i,n+1-j)上落子的。即,只要先手还能放,那下一步后手肯定也能放。

所以,最终先找不到合适位置落子的必然是先手。所以后手 保持与先手关于棋盘中心对称放子 是一种必胜的方法。所以先手无论如何放子,都是先手的必败态。

当n为奇数时,先手若选择放置在整张棋盘的中心点,而后跟随后手对称落子,则是先手的必胜态。具体说明方法与n为偶数时类似,不再赘述。

 #include<iostream>
#include<algorithm>
#include<cstdio>
#include<cstring>
using namespace std;
int main()
{
    int n;
    while(scanf("%d",&n)!=EOF)
    {
        if(n%==)
            cout<<<<endl;
        else
            cout<<<<endl;
    }
    return ;
}

1004

这是一道二进制题,题目上已经有提示了。n个树坑可以看成是n位二进制数,没有种树的位置上值为0,种树的位置上值为1。这样只需要枚举所有的n位二进制数,求出每一位上的值,再判断是否至少有1以及任意两个1之间是否距离至少为m。

 #include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring> using namespace std;
int a[]; int main()
{
int n,m,k;
while(~scanf("%d%d%d",&n,&k,&m))
{
int ans=;
for(int i=;i<(<<n);++i)
{
int cnt=;
memset(a,,sizeof(a));
int num=i;
while(num!=)
{
a[cnt++]=num%;
num=num/;
}
int count=,pos=;
num=;
bool f=true;
for(int j=;j<cnt;++j)
{
if(a[j]==)
{
if(num<m&&pos!=)
f=false;
count++;
num=;
pos++;
}
else
num++;
}
if(f&&count>=k)
ans++;
}
printf("%d\n",ans);
}
return ;
}

1005

签到题。将所有给出的数转化成10进制数,注意a~f的情况。用一个长度为1000的数组保存每个数出现的次数,最后遍历一遍数组找到出现次数最多的数即可。

 #include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring> using namespace std;
int num[];
char a[]={'a','b','c','d','e','f'};
int main()
{
int t,n;
char s[];
while(~scanf("%d",&t))
{
memset(num,,sizeof(num));
while(t--)
{
scanf("%d %s",&n,s);
int c=;
for(int i=;i<strlen(s);++i)
{
if(s[i]>=''&&s[i]<='')
{
c=c*n;
c+=s[i]-'';
}
else
{
c=c*n;
c+=s[i]-'a'+;
}
}
num[c]++;
}
int max=;
int ans=;
for(int i=;i<=;++i)
{
if(num[i]>max)
{
max=num[i];
ans=i;
}
}
printf("%d\n",ans);
}
return ;
}

1006

很经典的一道题,也算是签到题。解决这道题的方法很多,这里就只给出最优的方案。我们需要保存一个当前最大的子序列和maxsun以及从1开始的子序列的和thissum。当thissum>maxsum时,maxsum赋值为thissum,当thissum<0时,thissum赋值为0。这样遍历一遍数组,thissum每次加上遍历到的数,并进行更新,最后maxsum保存的便是最大的子序列和。

 #include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
using namespace std; int main()
{
long long ThisSum,MaxSum,i,a,n;
while(~scanf("%d",&n))
{ ThisSum = MaxSum = ;
for( i= ; i<n ; i++ )
{
scanf("%I64d",&a);
ThisSum += a; if( ThisSum > MaxSum )
MaxSum = ThisSum ;
else
if( ThisSum < )
ThisSum = ;
}
printf("%I64d\n",MaxSum);
}
return ;
}

1007

这道题是鼓励大家勇于提交的,给的两串数其实是没有规律的。而测试样例只有一组,那么唯一的可能就是测试样例在已经给出的数对里面。那么只要判断读入的字符串究竟是其中的哪一个就行了。

 #include<stdio.h>
#include<string.h>
char a[][]={
"",
"",
"",
"",
"",
"",
"",
"",
"",
""
};
char b[][]={
"",
"",
"",
"",
"",
"",
"",
"",
"",
""
};
int main(){
char s[];
scanf("%s",s);
for(int i=;i<;i++){
if(strcmp(s,a[i])==)
puts(b[i]);
}
}

1008

这道题是对凯撒加密的频数攻击,即依次枚举26个密钥,尝试用这些密钥将文章解密,得到26篇文章,然后比较这26篇文章与统计规律进行比较,找出最符合要求的文章即可。
重点是如何从26篇文章中筛选出最接近统计规律的文章。通常用的是如下的方法:
1、设p[i]表示26个字母中第i个字符的统计规律里的频率,我们计算所有26个字母对应的p[i]^2之和,这个值大约是0.065
2、设q[i]表示用当前密钥k解密后的文章中第i个字符的实际频率,我们计算sigma(p[i]*q[i])得到一个相关值m
3、对于26个密钥,找出相关值最接近0.065的那个密钥,那么这个就是最后的结果。

 #include<cstdio>
#include<cmath>
#include<cstring>
char c[];
double table[]={0.08167,0.01492,0.02782,0.04253,0.12702,0.0228,0.02015,0.06094,0.06966,0.00153,0.00772,0.04025,0.02406,0.06749,0.07507,0.01929,0.00095,0.05987,0.06327,0.09056,0.02758,0.00978,0.02360,0.00150,0.01974,0.00074};
double f[];
int cnt[]={};
int len,num;
void fun(){
for(int i=;i<len;i++){
if(c[i]>='a'&&c[i]<='z'){
cnt[c[i]-'a']++;
num++;
}else if(c[i]>='A'&&c[i]<='Z'){
cnt[c[i]-'A']++;
num++;
}
}
for(int i=;i<;i++){
f[i]=1.0*cnt[i]/num;
}
int key;
double k=;
for(int i=;i<;i++){
double test=;
for(int j=;j<;j++){
test+=table[(j-i+)%]*f[j];
}
if(fabs(test-0.065)<k){
key=i;
k=fabs(test-0.065);
}
}
for(int i=;i<len;i++){
if(c[i]>='a'&&c[i]<='z'){
putchar((c[i]-'a'-key+)%+'a');
}else if(c[i]>='A'&&c[i]<='Z'){
putchar((c[i]-'A'-key+)%+'A');
}else{
putchar(c[i]);
}
}
}
int main(){
//freopen("in.txt","r",stdin);
len=num=;
char tmp;
while(true){
tmp=getchar();
if(tmp==EOF||tmp=='#'){
fun();
len=num=;
memset(c,,sizeof c);
memset(cnt,,sizeof cnt);
if(tmp==EOF)
break;
putchar('#');
}else{
c[len++]=tmp;
}
}
}

1009

基本照着题目的要求写即可,有以下几个注意点:
1、1也是个无聊的数
2、输入的x和y的大小不确定,需要先比较一下
3、对于能表示成a^2+b^2的这个条件,实际上我们可以证明,一个奇素数,如果能够表示成为上述形式,那么当且仅当他模4的余数为1。如果没发现这个定理,其实打表也是可以卡时间过的。

 #include<cstdio>
using namespace std;
const int maxi=;
bool vis[maxi];
int sum[maxi];
int main(){
sum[]=;
sum[]=;
for(int i=;i<maxi;i++){
sum[i]=sum[i-];
if(!vis[i]){
if((i%==||i==)&&i%!=){
sum[i]++;
}
for(int j=;i*j<maxi;j++){
vis[i*j]=true;
}
}
}
int a,b;
while(scanf("%d%d",&a,&b)==){
if(a>b){
printf("%d\n",sum[a]-sum[b-]);
}else{
printf("%d\n",sum[b]-sum[a-]);
}
}
}

1010

一道模拟题,按照要求写,但是如果对每个样例都循环k次,那么这显然会超时。实际上对于每组输入并不需要循环这么多次,一般循环几次后就会看到循环的终点了,这里有两个终点,153和0,循环到这里就可以停了。

 #include<cstdio>
#include<algorithm>
#include<cstring>
#include<vector>
using namespace std;
const int maxi=;
int fun(int n,int k){
int cnt=;
while(true){
if(n==)
return ;
if(n==)
return ;
n-=n%;
n+=n%==?:(-n%);
int tmp=;
while(n>){
tmp+=(n%)*(n%)*(n%);
n/=;
}
n=tmp;
cnt++;
if(cnt==k)
return n;
}
}
int main(){
int n,k;
while(scanf("%d%d",&n,&k)==)
printf("%d\n",fun(n,k));
}

2015苏州大学ACM-ICPC集训队选拔赛(3)题解的更多相关文章

  1. 2014 ACM/ICPC 北京邀请赛 部分 题解

    题目链接:http://acm.bnu.edu.cn/bnuoj/problem.php?search=2014+ACM-ICPC+Beijing+Invitational+Programming+C ...

  2. hihocoder1257(构造)(2015北京ACM/ICPC)

    题意: 给你n条蛇,a[i]的长度为i,要求组成一个矩形.奇数蛇可折叠奇数次,偶数蛇折叠偶数次,然后按蛇的次序输出 (即一条蛇的输出只能是一个方向的) 2 3 1 2 1 3 2 3 1 1 2 1 ...

  3. 2015 ACM / ICPC 亚洲区域赛总结(长春站&北京站)

    队名:Unlimited Code Works(无尽编码)  队员:Wu.Wang.Zhou 先说一下队伍:Wu是大三学长:Wang高中noip省一:我最渣,去年来大学开始学的a+b,参加今年区域赛之 ...

  4. ACM ICPC 2015 Moscow Subregional Russia, Moscow, Dolgoprudny, October, 18, 2015 G. Garden Gathering

    Problem G. Garden Gathering Input file: standard input Output file: standard output Time limit: 3 se ...

  5. ACM ICPC 2015 Moscow Subregional Russia, Moscow, Dolgoprudny, October, 18, 2015 D. Delay Time

    Problem D. Delay Time Input file: standard input Output file: standard output Time limit: 1 second M ...

  6. hdu 5444 Elven Postman(二叉树)——2015 ACM/ICPC Asia Regional Changchun Online

    Problem Description Elves are very peculiar creatures. As we all know, they can live for a very long ...

  7. 2016 ACM/ICPC Asia Regional Qingdao Online(2016ACM青岛网络赛部分题解)

    2016 ACM/ICPC Asia Regional Qingdao Online(部分题解) 5878---I Count Two Three http://acm.hdu.edu.cn/show ...

  8. (并查集)Travel -- hdu -- 5441(2015 ACM/ICPC Asia Regional Changchun Online )

    http://acm.hdu.edu.cn/showproblem.php?pid=5441 Travel Time Limit: 1500/1000 MS (Java/Others)    Memo ...

  9. (二叉树)Elven Postman -- HDU -- 54444(2015 ACM/ICPC Asia Regional Changchun Online)

    http://acm.hdu.edu.cn/showproblem.php?pid=5444 Elven Postman Time Limit: 1500/1000 MS (Java/Others)  ...

  10. 2015 ACM/ICPC Asia Regional Changchun Online HDU 5444 Elven Postman【二叉排序树的建树和遍历查找】

    Elven Postman Time Limit: 1500/1000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others)T ...

随机推荐

  1. 关于华为P9手机的解锁、刷Recovery、获取Root、安装Busybox,以及升级降级的全过程(和一些错误的解决方法)

    我有一部华为P9手机,型号EVA-TL00,属于移动定制机.用了半年多了,想给手机添加一些功能,发现有些功能必须Root之后才能用代码实现,所以动了Root的打算. 一.手机解锁.(不解锁则无法对手机 ...

  2. android - 解决“应用自定义权限重名”

    背景 现场的开发今天跟我说,测试包装不上!报错"应用自定义权限重名"!!! 网上百度下关键字,发现魅族手机有这个毛病,顺藤摸瓜:"http://bbs.flyme.cn/ ...

  3. (转)java提高篇(四)-----理解java的三大特性之多态

    面向对象编程有三大特性:封装.继承.多态. 封装隐藏了类的内部实现机制,可以在不影响使用的情况下改变类的内部结构,同时也保护了数据.对外界而已它的内部细节是隐藏的,暴露给外界的只是它的访问方法. 继承 ...

  4. 阿里云服务器Windows Server 2008/2012部署Office Web Server 2013

    以前成功将Office Web Server 2013部署在了本地服务器上,此次是将Office Web Server 2013部署在阿里云服务器Windows Server 2008和2012上,中 ...

  5. cesium 获取点击点的高程

    var picklHandler = new Cesium.ScreenSpaceEventHandler(viewer.scene.canvas);picklHandler .setInputAct ...

  6. 9. leetcode 389. Find the Difference

    Given two strings s and t which consist of only lowercase letters. String t is generated by random s ...

  7. 拓扑排序下的有无环判定 STL方法

    bool canFinish(int numCourses, vector<pair<int, int>>& prerequisites) { vector<se ...

  8. CentOS上javaweb开发环境搭建

    CentOS上javaweb开发环境搭建 安装jdk yum list java* yum install java-1.7.0-openjdk* -y java -version 安装tomcat ...

  9. ABP+AdminLTE+Bootstrap Table权限管理系统第七节--登录逻辑及abp封装的Javascript函数库

    经过前几节,我们已经解决数据库,模型,DTO,控制器和注入等问题.那么再来看一下登录逻辑.这里算是前面几节的一个初次试水. 首先我们数据库已经有的相应的数据. 模型和DTO已经建好,所以我们直接在服务 ...

  10. Java Socket 编程

    1. 背景 网络编程是指编写运行在多个设备(计算机)的程序,这些设备都通过网络连接起来. java.net 包中 J2SE 的 API 包含有类和接口,它们提供低层次的通信细节.你可以直接使用这些类和 ...