**走格子**
基准时间限制:1 秒 空间限制:131072 KB 分值: 5
有编号1-n的n个格子,机器人从1号格子顺序向后走,一直走到n号格子,并需要从n号格子走出去。机器人有一个初始能量,每个格子对应一个整数A[i],表示这个格子的能量值。如果A[i] > 0,机器人走到这个格子能够获取A[i]个能量,如果A[i] < 0,走到这个格子需要消耗相应的能量,如果机器人的能量 < 0,就无法继续前进了。问机器人最少需要有多少初始能量,才能完成整个旅程。
例如:n = 5。{1,-2,-1,3,4} 最少需要2个初始能量,才能从1号走到5号格子。途中的能量变化如下3 1 0 3 7。
Input
第1行:1个数n,表示格子的数量。(1 <= n <= 50000)
第2 - n + 1行:每行1个数A[i],表示格子里的能量值(-1000000000 <= A[i] <= 1000000000)
Output
输出1个数,对应从1走到n最少需要多少初始能量。
Input示例
5
1
-2
-1
3
4
Output示例
2
#include
#include
#include
using namespace std;
int main()
{
long long int m,n,s=0,i;
long long int minn=0x3f3f3f3f;
scanf("%lld",&n);
for(i=0;iscanf("%lld",&m);
s+=m;
if(sif(minn>=0)
printf("0\n");
else
printf("%lld\n",0-minn);
return 0;
}
**扔盘子**
基准时间限制:1 秒 空间限制:131072 KB 分值: 10
有一口井,井的高度为N,每隔1个单位它的宽度有变化。现在从井口往下面扔圆盘,如果圆盘的宽度大于井在某个高度的宽度,则圆盘被卡住(恰好等于的话会下去)。
盘子有几种命运:1、掉到井底。2、被卡住。3、落到别的盘子上方。
盘子的高度也是单位高度。给定井的宽度和每个盘子的宽度,求最终落到井内的盘子数量。
如图井和盘子信息如下:
井:5 6 4 3 6 2 3
盘子:2 3 5 2 4
最终有4个盘子落在井内。
本题由 @javaman 翻译。
Input
第1行:2个数N, M中间用空格分隔,N为井的深度,M为盘子的数量(1 <= N, M <= 50000)。
第2 - N + 1行,每行1个数,对应井的宽度Wi(1 <= Wi <= 10^9)。
第N + 2 - N + M + 1行,每行1个数,对应盘子的宽度Di(1 <= Di <= 10^9)
Output
输出最终落到井内的盘子数量。
Input示例
7 5
5
6
4
3
6
2
3
2
3
5
2
4
Output示例
4
这个题目正着来做肯定比较麻烦,可以试着简化一下
#include
#include
#include
#include
using namespace std;
int main()
{
int n,m;
int i,j;
int a[50005],b[50005];
scanf("%d %d",&n,&m);
for(i=0;iscanf("%d",&a[i]);
for(i=0;iscanf("%d",&b[i]);
for(i=1;i1],a[i]);//从井口向下进行初始化,只有上面的横截面积比下面的横截面积大才有意义
int count=0;
for(i=0;ifor(n--;n>=0;n--)//当前盘子可以卡住的话数目加1,继续判断下一个盘子情况
{
if(a[n]>=b[i])
break;
}
if(n>=0)
count++;
}
printf("%d\n",count);
return 0;
}
**独木舟**
基准时间限制:1 秒 空间限制:131072 KB 分值: 10
n个人,已知每个人体重。独木舟承重固定,每只独木舟最多坐两个人,可以坐一个人或者两个人。显然要求总重量不超过独木舟承重,假设每个人体重也不超过独木舟承重,问最少需要几只独木舟?
Input
第一行包含两个正整数n (0
首先将人的体重升序排列,再从两头一起开始判断
#include
#include
#include
#include
using namespace std;
int main()
{
int n,m;
int a[10005],b[10005],i,j;
memset(b,0,sizeof(b));
scanf("%d %d",&n,&m);
int k=n-1,sum=0;
for(i=0;iscanf("%d",&a[i]);
sort(a,a+n);
for(i=0;i<=k;i++)
{
int flag=0;
if(b[i]==0)
{
for(j=k;j>=i;j--)
if(b[j]==0&&a[i]+a[j]<=m)
{
sum++;
b[i]=1;
b[j]=1;
flag=1;
//k=j-1;
break;
}
if(flag==0)
{
b[i]=1;
sum++;
}
}
}
printf("%d\n",sum);
return 0;
}
**斜率最大**
基准时间限制:1 秒 空间限制:131072 KB 分值: 20
平面上有N个点,任意2个点确定一条直线,求出所有这些直线中,斜率最大的那条直线所通过的两个点。
(点的编号为1-N,如果有多条直线斜率相等,则输出所有结果,按照点的X轴坐标排序,正序输出。数据中所有点的X轴坐标均不相等,且点坐标为随机。)
Input
第1行,一个数N,N为点的数量。(2 <= N <= 10000)
第2 - N + 1行:具体N个点的坐标,X Y均为整数(-10^9 <= X,Y <= 10^9)
Output
每行2个数,中间用空格分隔。分别是起点编号和终点编号(起点的X轴坐标 < 终点的X轴坐标)
Input示例
5
1 2
6 8
4 4
5 4
2 3
Output示例
4 2
刚开始是用常规方法做,当然时间超了
后来才知道可以用数学结论节省时间
先把这些点按x坐标从小到大排序,斜率最大的两点必然是挨一起的两个点,所以排序O(n* lg n),遍历一次O(n)就够了
详细解释看这里
#include
#include
#include
#include
using namespace std;
struct node
{
int x;
int y;
int z;
double d;
};
int cmp(node a,node b)
{
a.x.x;
}
int main()
{
int n;
int i,j;
double t;
node a[10005],d;
scanf("%d",&n);
for(i=0;i
{
scanf("%d %d",&a[i].x,&a[i].y);
a[i].z=i;
}
for(i=0;i
for(j=i+1;j
{
if(a[i].x>a[j].x)
{
d.x=a[i].x;
d.y=a[i].y;
d.z=a[i].z;
a[i].x=a[j].x;
a[i].y=a[j].y;
a[i].z=a[j].z;
a[j].x=d.x;
a[j].y=d.y;
a[j].z=d.z;
}
}
double maxn=-0x3f3f3f3f;
for(i=0;i
{
if(a[i].x!=a[i+1].x)
{
double t=(a[i+1].y-a[i].y)*1.0/(a[i+1].x-a[i].x);
a[i].d=t;
if(maxn;
}
}
for(i=0;i
{
if(maxn==a[i].d)
{
printf("%d %d\n",a[i].z+1,a[i+1].z+1);
}
}
return 0;
}
数据流中的算法
基准时间限制:1.5 秒 空间限制:131072 KB 分值: 20
51nod近日上线了用户满意度检测工具,使用高级人工智能算法,通过用户访问时间、鼠标轨迹等特征计算用户对于网站的满意程度。
现有的统计工具只能统计某一个窗口中,用户的满意程度的均值。夹克老爷想让你为统计工具添加一个新feature,即在统计均值的同时,计算窗口中满意程度的标准差和中位数(均值需要向下取整)。
Input
第一行是整数n与k,代表有n次操作,时间窗口大小为k。
(1 <= n <= 10^6, 1 <= k <= 100)
接下来的n行,每行代表一次操作。操作有“用户访问”、“查询均值”、“查询方差”、“查询中位数”四种。每行的第一个数代表操作类型。
操作数1:用户访问
输入格式:<1, v>
用户的满意度v为闭区间[0, 100]中的任意整数。用户每访问一次,数据更新,移动统计窗口。
操作数2:查询均值
输入格式:<2>
统计窗口内的用户满意度的均值。
操作数3:查询方差
输入格式:<3>
统计窗口内用户满意度的方差
操作数4:查询中位数
输入格式:<4>
统计窗口内用户满意度的中位数
p.s. 在有查询请求时,窗口保证不为空
p.s.s. 有查询请求时,窗口可能不满
Output
对于“查询均值”、“查询方差”、“查询中位数”操作的结果,输出保留两位小数。
Input示例
12 3
1 1
1 2
1 3
2
3
4
1 4
1 5
1 6
2
3
4
Output示例
2.00
0.67
2.00
5.00
0.67
5.00
k的用处题目描述的不清楚,可以理解为该统计工具所能保存的数据个数
比较复杂的一道模拟题
特别是求中位数时容易超时,由于满意度的取值范围不大,用户的满意度v为闭区间[0, 100]中的任意整数,所以可用一个稍大于100数组来存放用户的满意度,就可避免超时
#include
#include
int main()
{
int n,k,now;
int i,j,a[105],ss[105];
scanf("%d %d",&n,&k);
for(i=0;i1;
char s[10];
int ii=-1;
getchar();
now=0;
for(i=0;i<=100;i++)
ss[i]=0;
for(int iii=0;iii//printf("iii:%d\n",iii);
gets(s);
int t=0;
if(s[0]=='1')
{
int len=strlen(s);
for(i=2;iif(s[i]>='0'&&s[i]<='9')
t=t*10+s[i]-'0';
ii++;
ss[a[ii%k]]--;
a[ii%k]=t;
ss[a[ii%k]]++;
if(iielse if(s[0]=='2')
{
int sum=0;
int tt=0;
for(i=0;iif(a[i]!=-1)
{
tt++;
sum+=a[i];
}
}
if(tt!=0)
{
int su=sum/tt;
sum=su;
printf("%d.00\n",su);
}
}
else if(s[0]=='3')
{
double sum=0,s=0;
int tt=0;
for(int i=0;iif(a[i]!=-1)
{
tt++;
sum+=a[i];
}
}
if(tt!=0)
sum=sum*1.0/tt;
for(int i=0;iif(a[i]!=-1)
s+=(a[i]-sum)*(a[i]-sum);
}
s=s/tt;
printf("%.2lf\n",s);
}
else if(s[0]=='4')
{
int flag=0,tlag;
int ttt;
if(now%2!=0)
{
ttt=-1;
for(int kk=0;kk<=100;kk++)
{
if(flag==0)
{
ttt+=ss[kk];//printf("ttt:%d\n",ttt);
if(ttt>=now/2)
{
printf("%.2lf\n",(double)kk);
flag=1;
}
}
}
}
else
{
int st,ed;
int rlag=0;
tlag=0,flag=0;
ttt=-1;
for(int kk=0;kk<=100;kk++)
{
//printf("ss[%d]:%d\n",kk,ss[kk]);
if(tlag==0||flag==0)
{
ttt+=ss[kk];//printf("ttt:%d\n",ttt);
if(ttt>=now/2-1&&tlag==0)
{
st=kk;
tlag=1;
}
if(ttt>=now/2&&flag==0)
{
ed=kk;
flag=1;
}
}
if(tlag==1&&flag==1&&rlag==0)
{
printf("%.2lf\n",(double)(st+ed)/2);
rlag=1;
}
}
}
}
}
return 0;
}