6月5日下午刚上完高数课,老师没留作业,正好有空把贪心开了,这几天程设敲下来感觉也不是没有收获,很多上学期初学的也能理解较为透彻了,无论递推递归还是贪心动规,理解思想最重要,一味记例题没有意义,多敲题,多思考,最后还是祝所有人期末能AK~ 总题目链接
一开始没考虑全面,认为每次直接贪掉所有数字里面最大的就行,但是如10230450删两个就变成了102300其实最小是删1和3变成200。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
char s[101];
int n;
while(~scanf("%s %d",s,&n))
{
int m=strlen(s);
while(n--)
{
int i=0;
while(s[i]<=s[i+1]&&i+1<m)//不能少了等于好
{
i++;
}
if(i!=m-1)
for(int j=i;j<m;j++)
{
s[j]=s[j+1];
}
m--;
// for(int k=0;k<m;k++)
// printf("%c",s[k]);
// printf("\n");
}
int i=0;
while(s[i]=='0'&&i<m) i++;
if(i==m) printf("0\n");
else
{
for(int j=i;j<m;j++)
printf("%c",s[j]);
printf("\n");
}
}
return 0;
}
注意编号1-n ,每次在当前时间选结束最早的就行,按结束时间排序就行。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct node
{
int begin,end,num;
} a[101],t;
int main()
{
int n;
scanf("%d",&n);
for(int i=0; i<n; i++)
{
scanf("%d %d",&a[i].begin,&a[i].end);
a[i].num=i+1;
}
for(int i=0; i<n-1; i++)
{
for(int j=0; j<n-i-1; j++)
{
if(a[j].end>a[j+1].end)
{
t=a[j];
a[j]=a[j+1];
a[j+1]=t;
}
}
}
int now=a[0].end;
printf("%d",a[0].num);
for(int i=1; i<n; i++)
{
if(a[i].begin>=now)
{
printf(",%d",a[i].num);
now=a[i].end;
}
}
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct node
{
int begin,end;
} a[101],t;
int main()
{
int n;
while(~scanf("%d",&n))
{
for(int i=0; i<n; i++)
{
scanf("%d %d",&a[i].begin,&a[i].end);
}
for(int i=0; i<n-1; i++)
{
for(int j=0; j<n-i-1; j++)
{
if(a[j].end>a[j+1].end)
{
t=a[j];
a[j]=a[j+1];
a[j+1]=t;
}
}
}
int now=0;
int ans=0;
for(int i=0; i<n; i++)
{
if(a[i].begin>=now)
{
ans++;
now=a[i].end;
}
}
printf("%d\n",ans);
}
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
//冒泡模板flag判断升序降序
void sort(int *a,int n,int flag)
{
int t;
if(flag)
{
for(int i=0; i<n; i++)
{
for(int j=0; j<n-i-1; j++)
{
if(a[j]>a[j+1])
{
t=a[j];
a[j]=a[j+1];
a[j+1]=t;
}
}
}
}
else
{
for(int i=0; i<n; i++)
{
for(int j=0; j<n-i-1; j++)
{
if(a[j]<a[j+1])
{
t=a[j];
a[j]=a[j+1];
a[j+1]=t;
}
}
}
}
}
int main()
{
int n,m;
int a[201],dis[201];
while(~scanf("%d %d",&n,&m))
{
for(int i=0;i<n;i++)
scanf("%d",&a[i]);
if(n<=m)
printf("%d\n",n);
else
{
sort(a,n,1);
for(int i=0;i<n-1;i++)
dis[i]=a[i+1]-a[i]-1;
sort(dis,n-1,0);
int ans=a[n-1]-a[0]+1;
for(int i=0;i<m-1;i++)
ans-=dis[i];
printf("%d\n",ans);
}
}
return 0;
}
用一个数组a记录每套系统的最大拦截高度,每次拦截导弹先从小到大遍历数组a,若能拦截则更新那个拦截系统的最大高度,否则再弄一个新的拦截系统
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
int n;
int a[201],x;
while(~scanf("%d",&n))
{
memset(a,-1,sizeof(a));
int m=0;
while(n--)
{
scanf("%d",&x);
int i;
for(i=0;i<m;i++)
if(x<=a[i])
{
a[i]=x;
break;
}
if(i==m)
{
a[m++]=x;
}
}
printf("%d\n",m);
}
return 0;
}
这题只要买过东西的都会做吧…
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct node
{
int p,h;
}a[1001],t;
int main()
{
int T;
scanf("%d",&T);
while(T--)
{
int n,m;
scanf("%d %d",&n,&m);
for(int i=0;i<m;i++)
{
scanf("%d %d",&a[i].p,&a[i].h);
}
for(int i=0; i<m; i++)
{
for(int j=0; j<m-i-1; j++)
{
if(a[j].p>a[j+1].p)
{
t=a[j];
a[j]=a[j+1];
a[j+1]=t;
}
}
}
double ans=0;
int i;
for(i=0;i<m;i++)
{
if(a[i].h*a[i].p>n)
{
break;
}
ans+=a[i].h*1.0;
n-=a[i].h*a[i].p;
}
ans=ans+n*1.0/a[i].p;
printf("%.2f\n",ans);
}
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct node
{
int p,h;
}a[10001],t;
void sort(int l,int r)//快排
{
t=a[l];
int i=l,j=r;
if(l>=r) return;
while(i<j)
{
while((a[j].h>t.h||(a[j].h==t.h&&a[j].p<=t.p))&&i<j) j--;
a[i]=a[j];
while((a[i].h<t.h||(a[i].h==t.h&&a[i].p>=t.p))&&i<j) i++;
a[j]=a[i];
}
a[i]=t;
sort(l,i-1);
sort(i+1,r);
}
int main()
{
int n,m;
while(~scanf("%d %d",&n,&m))
{
for(int i=0;i<n;i++)
{
scanf("%d %d",&a[i].h,&a[i].p);
}
sort(0,n-1);
int ans=0;
for(int i=0;i<m;i++)
ans+=a[i].p;
printf("%d\n",ans);
}
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct node
{
int p,h,x;
} a[10001],t;
void sort(int l,int r)
{
t=a[l];
int i=l,j=r;
if(l>=r)
return;
while(i<j)
{
while(a[j].x<=t.x&&i<j) j--;
a[i]=a[j];
while(a[i].x>=t.x&&i<j) i++;
a[j]=a[i];
}
a[i]=t;
sort(l,i-1);
sort(i+1,r);
}
int main()
{
int m;
scanf("%d",&m);
for(int i=0; i<10; i++)
{
scanf("%d %d",&a[i].p,&a[i].h);
a[i].x=a[i].p/a[i].h;
}
sort(0,9);
int ans=0;
int i;
for(i=0; i<10; i++)
{
if(a[i].h<=m)
{
ans+=a[i].p;
m-=a[i].h;
}
else
{
ans+=m*a[i].x;
break;
}
}
printf("%d\n",ans);
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int a[10000001],t;
void sort(int l,int r)
{
t=a[l];
int i=l,j=r;
if(l>=r)
return;
while(i<j)
{
while(a[j]<=t&&i<j)
j--;
a[i]=a[j];
while(a[i]>=t&&i<j)
i++;
a[j]=a[i];
}
a[i]=t;
sort(l,i-1);
sort(i+1,r);
}
int main()
{
int m,n;
while(~scanf("%d %d",&n,&m))
{
for(int i=0; i<n; i++)
{
int x,y;
scanf("%d %d",&x,&y);
a[i]=y-x;
}
sort(0,n-1);
int ans=0;
for(int i=0; i<m; i++)
{
ans+=a[i];
}
printf("%d\n",ans);
}
return 0;
}
注意是要买更多的苹果,所以是比质量/价格
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
struct node
{
int p,h;
double x;
} a[10001],t;
void sort(int l,int r)
{
t=a[l];
int i=l,j=r;
if(l>=r)
return;
while(i<j)
{
while(a[j].x<=t.x&&i<j)
j--;
a[i]=a[j];
while(a[i].x>=t.x&&i<j)
i++;
a[j]=a[i];
}
a[i]=t;
sort(l,i-1);
sort(i+1,r);
}
int main()
{
int m,n;
while(~scanf("%d %d",&n,&m)&&m!=-1&&n!=-1)
{
for(int i=0; i<m; i++)
{
scanf("%d %d",&a[i].h,&a[i].p);
a[i].x=a[i].h*1.0/a[i].p*1.0;
}
sort(0,m-1);
double ans=0;
int i;
for(i=0; i<m; i++)
{
if(a[i].p<=n)
{
ans+=1.0*a[i].h;
n-=a[i].p;
}
else
{
ans+=n*1.0*a[i].x;
break;
}
}
printf("%.3f\n",ans);
}
return 0;
}
这次小鑫出场率真高,堪比数学界的小明,英语界的李华。
贪心问题用于求一个问题的最优解,如果能保证每次操作都是此次操作所有可能最优的一个,那么就能求出最优解,贪心原理好理解,但有些题还是需要一定思维,此章节顺带还会考排序,需要注意。