A:六舍七入 10/20;
B:俄罗斯方块 10/20;
C:月份矩阵 2/20;
D:杜拉拉寻宝 19/20.
A:
{
此题的思路不算难想,就是复杂了点(本人1A)
思路如下:
此题数据中可能含有小数点和符号,所以不适宜直接读入,可以使用读入到char或string类型里
本人对此还附加了把char里的数字读入到int类型的mapn数组里的操作,负号另开变量记录,小数点用-2表示
接着for循环搜索小数点的位置,记录到poi里
得到poi的值,进行一次分类讨论:
1,是否不存在小数部分(直接输出,并加上“.00”)
2,是否小数部分只有两位(直接输出)
3,否则继续执行下面代码
接下来的代码需要处理的数据都是正常的了,之所谓正常者,小数点后多于三位也
好似123.997和-342.11678一样
当然,“六舍七入”至小数点后两位和“四舍五入”至小数点后两位其实是一样的道理,真正重要的是千分位,再往后的都和答案没关系
接下来用if判断千分位是否大于等于7,是就进一,否就输出千分位以前的值
如果进一了,那么需要一个for循环从后往前像数学上的一样传递进一后的影响(需要注意跳开小数点和对最高位的进一处理)
for循环结束后,进行的就是输出环节
首先,判断是否有符号,有就输出
接着把整数位的0删除到只剩一个
最后输出主体,当然,千分位以后的就不用输出了
That‘s all.It's easy,isn't it?
接下来给出本人的程序(可能和以上讲的略有不同):
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
using namespace std;
int n;
char ch[1100];
int mapn[1100];
int work()
{
memset(mapn,0,sizeof(mapn));
cin>>ch;
int zf=1;
int poi=-1;
int l=strlen(ch);
for(int i=1;i<=l;i++)
{
if(ch[i-1]=='.') mapn[i]=-1,poi=i;
else
if(ch[i-1]=='-') zf=0,mapn[i]=0;
else mapn[i]=ch[i-1]-'0';
}
if(poi==-1)
{
cout<<ch<<".00"<<endl;return 0;
}
if(poi==l-2)
{
cout<<ch<<endl;return 0;
}
int nl=poi+2;
if(mapn[nl+1]>=7) mapn[nl]+=1;
if(mapn[nl]>=10)
{
for(int i=nl;i>=1;i--)
{
if(mapn[i]>=10)
{
int t=1;
if(mapn[i-1]==-1) t=2;
mapn[i-t]+=mapn[i]/10;
mapn[i]%=10;
}
}
}
if(mapn[0]!=0) cout<<mapn[0];
int b=1; if(mapn[b]==0) b=2;
if(!zf) cout<<'-';
if(poi-1<b) cout<<0;
for(int i=b;i<=nl;i++)
{
if(mapn[i]>=0) cout<<mapn[i];
else cout<<'.';
}
cout<<endl;
}
int main()
{
cin>>n;
for(int d=1;d<=n;d++)
{
work();
}
return 0;
}
最后注意,由于是多组数据,所以要记得初始化哦~
}
B:
{
本题也不算太难,主要要找对策略(贪心)(1A)
读题可以发现,删除方块的方法有两种截(横向删除)和斩(纵向删除)
可以看出横向删除是群伤,而纵向删除是个体伤害
当数据多时,横向删除其实是最划算的
所以应该尽量进行横向删除,剩下的再使用纵向删除
得出解法:
使用for循环从开头截去i行(0<=i<=最大值),其余方块则斩掉的情况
并记录下所用步数,最后输出最小值
没错,就是这么简单……
给出程序如下:
#include<iostream>
#include<cmath>
#include<algorithm>
#include<cstring>
using namespace std;
int t;
int mapn[10000001];
int work()
{
int ans=9999,m=-1,n;
cin>>n;int peo=n;
for(int i=1;i<=n;i++)
{
cin>>mapn[i];m=max(m,mapn[i]);
}
for(int i=0;i<=m;i++)
{
peo=i;
for(int j=1;j<=n;j++)
if(mapn[j]>i) peo++;
ans=min(ans,peo);
}
cout<<ans<<endl;
}
int main()
{
cin>>t;
for(int d=1;d<=t;d++)
{
work();
}
return 0;
}
需要注意循环横向删除时循环的范围哦(上文已给出)~
}
C:
{
太简单了,枚举,肯定不会超时的
给出本人程序,当然是使用比较特殊的操作的:
#include<iostream>
#include<cmath>
#include<algorithm>
#include<cstring>
using namespace std;
int t,n,m;
int mapn[3033][3033];
int work()
{
memset(mapn,-1,sizeof(mapn));
int k=0;
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
{
cin>>mapn[i][j];
if(mapn[i-1][j]==mapn[i][j]||mapn[i][j-1]==mapn[i][j]) k=1;
}
if(k) cout<<"WRONG"<<endl;
else cout<<"RIGHT"<<endl;
return 0;
}
int main()
{
cin>>t>>n>>m;
for(int d=1;d<=t;d++)
{
work();
}
}
}
D:
{
并没看懂题目,自然也没有AC
但给出一点提示,但愿你能打破无人AC的窘境
如下: