P1478 陶陶摘苹果(升级版)
1.思路
看到这道题的时候就想着使用二维数组存放数,先判定能否够得着,然后存入数组中,再排序。
最后计数,但这样写还是错了,不知道该怎么改进,只能看大佬的思路了。
大佬的思路十分的好理解:
1.核心就是用桶排序,先将能够得着的找到,然后数组存放所要花的力气(for循环,相同就加1)
2.最后再用for循环,用剩下的力气减去每个苹果要花的力气。
2.源码
#include<stdio.h>
int c[101];//定义一百个桶子,c[i]代表用i个力气能摘到的苹果的数目
int main(){
int n,s,h,a,b,i,t=0;
scanf("%d %d\n %d %d",&n,&s,&h,&i);
h+=i;//输入,借用"i"将淘淘用凳子达到的最大高度复制给"h"
for(i=1;i<=n;i++){
scanf("%d %d",&a,&b);
if(a<=h)
c[b]++;//如果能摘到,就在用b个力气能摘到苹果的桶子中加一
}
//接下来 按力气从小到大选苹果
for(i=0;i<=100&&s>=0;i++){//注意要从"0"开始,有苹果是免费的
while(c[i]){//一个桶子里也可有多个苹果
s-=i;//减去摘这个苹果的力气
t++;//摘到的苹果数加一
c[i]--;//桶里的苹果减一个
if(s<0){//当力气没了时结束
t--;//这个苹果没有足够力气摘不了(s<0)
/*
这样有个缺陷,当所有都能摘下时,没有输出
printf("%d",t);,
return 0;
*/
}
}
}
printf("%d",t);
return 0;
}
3.错误示范
#include<stdio.h>
int main(){
int n,s;
scanf("%d %d",&n,&s); //苹果n,力气s
int a,b; //椅子a,手长b
scanf("%d %d",&a,&b);
int j=0,c[5001][2];
int num[5001][2]={0};
for(int i=0;i<n;i++){
scanf("%d %d",&c[i][0],&c[i][1]);
if(a+b>=c[i][0]){
num[j][0]=c[i][0];
num[j][1]=c[i][1];
j++;
}
}
int len=j,m,p;
for(int i=0;i<len-1;i++){
for(int t=i+1;t<len;t++){
if(num[i][1]>num[t][1]){
m=num[i][1];
num[i][1]=num[t][1];
num[j][1]=m;
p=num[i][0];
num[i][0]=num[t][0];
num[j][0]=p;
}
}
}
int sum=0;
for(int i=0;i<len;i++){
sum+=num[i][1];
if(sum==s)
printf("%d",i+1);
else if(sum>s){
printf("%d",i+1);
break;
}
}
思路
直接根据体力排序,把体力小的排在前面。
然后再判断是否满足:能否够得到和体力是否够
源码
#include<bits/stdc++.h>
using namespace std;
struct apple{
int x,y;//x苹果的高度,y要花的力气
}p[6000];
int n,s;
int a,b;
int cmp(apple a,apple b){
return a.y<b.y;
}
int main(){
int max_height=0;
cin>>n>>s;
cin>>a>>b;
max_height=a+b;
for(int i=1;i<=n;i++){
cin>>p[i].x>>p[i].y;
}
sort(p+1,p+1+n,cmp);
int cnt=0;//统计能摘到的苹果
for(int i=1;i<=n;i++){
if(max_height>=p[i].x&&s>=p[i].y){
cnt++;
s-=p[i].y;
}
}
cout<<cnt<<endl;
}