地址:http://www.bnuoj.com/bnuoj/contest_show.php?cid=3114
A题 : HDU 1969 二分
注意PI要用acos(-1.0)表示
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<queue>
#include<iostream>
const double pi = acos(-1.0);
const double eps = 1e-6;
using namespace std;
double s[10005];
int main()
{
int i,n,f,t,ri,sum;
double mid,max,min;
scanf("%d",&t);
while(t--)
{
max=min=0;
scanf("%d%d",&n,&f);
f++;
for(i=0;i<n;i++)
{
scanf("%d",&ri);
s[i]=ri*ri*pi;
if(s[i]>max) max=s[i];
}
while(max-min>=eps)
{
sum=0;
mid=(max+min)/2;
for(i=0;i<n;i++) sum+=s[i]/mid;
if(sum<f) max=mid;
else min=mid;
}
printf("%.4lf\n",mid);
}
return 0;
}
B题:POJ 1852 水题
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string.h>
#include<ctype.h>
#include<stack>
#include<queue>
#include<set>
#include<algorithm>
#include <limits.h>
using namespace std;
int a[100005];
int main()
{
int t,i,l,n,maxm,b;
scanf("%d",&t);
while(t--)
{
maxm=0;
scanf("%d%d",&l,&n);
for(i=0;i<n;i++)
{
scanf("%d",&a[i]);
b=min(l-a[i],a[i]);
if(b>maxm) maxm=b;
}
sort(a,a+n);
printf("%d %d\n",maxm,max(l-a[0],a[n-1]));
}
return 0;
}
C题: HDU 2102 三维BFS
三维的BFS,看似麻烦其实也差不多,莫名其妙MLE了好几次
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string.h>
#include<ctype.h>
#include<stack>
#include<queue>
#include<set>
#include<algorithm>
#include <limits.h>
using namespace std;
char mapp[2][11][11];
int dir[4][2]= {-1,0,0,-1,1,0,0,1};
typedef struct {
int x,y,time,floor;
}Node;
int main()
{
char x;
int t,n,m;
int ex,ey,ez;
int c,i,j;
scanf("%d",&c);
while(c--)
{
scanf("%d%d%d",&n,&m,&t);
x=getchar();
for(i=0; i<n; i++)
{
for(j=0; j<m; j++)
{
cin>>mapp[0][i][j];
if(mapp[0][i][j]=='P')
{
ex=0;
ey=i;
ez=j;
}
}
}
for(i=0; i<n; i++)
{
for(j=0; j<m; j++)
{
cin>>mapp[1][i][j];
if(mapp[1][i][j]=='P')
{
ex=1;
ey=i;
ez=j;
}
}
}
queue<Node>q;
Node th,ne;
th.x=0;
th.y=0;
th.floor=0;
th.time=0;
mapp[th.floor][th.x][th.y]='*';
q.push(th);
int safe=0;
while(!q.empty())
{
th=q.front();
q.pop();
if(th.time>t)
{
break;
}
if(th.x==ey&&th.y==ez&&th.floor==ex)
{
safe=1;
break;
}
for(i=0; i<4; i++)
{
ne.x=th.x+dir[i][0];
ne.y=th.y+dir[i][1];
ne.time=th.time+1;
ne.floor=th.floor;
if(ne.x<0||ne.y<0||ne.x>=n||ne.y>=m)
continue;
if(mapp[ne.floor][ne.x][ne.y]=='#')
{
mapp[ne.floor][ne.x][ne.y]='*';
ne.floor^=1;
if(mapp[ne.floor][ne.x][ne.y]=='#')
{
mapp[0][ne.x][ne.y]=mapp[1][ne.x][ne.y]='*';
continue;
}
}
if(mapp[ne.floor][ne.x][ne.y]=='.'||mapp[ne.floor][ne.x][ne.y]=='P')
{
q.push(ne);
mapp[ne.floor][ne.x][ne.y]='*';
}
}
}
if(safe)
cout<<"YES"<<endl;
else cout<<"NO"<<endl;
}
return 0;
}
D题: HDU 4337 DFS
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<queue>
#include<iostream>
const double pi = acos(-1.0);
const double eps = 1e-6;
using namespace std;
int visit[160];
int mapp[160][160];
int n,lu[160],flag;
bool dfs(int x,int t)
{
if(visit[x]) return false;
lu[t]=x;
visit[x]=1;
if(t==n&&mapp[1][x])
{
flag=1;
return true;
}
else
{
for(int i=1;i<=n;i++)
{
if(mapp[i][x]&&!visit[i])
{
if(dfs(i,t+1))
return true;
}
}
}
visit[x]=0;
return false;
}
int main()
{
int i,x,y,m;
while(scanf("%d%d",&n,&m)!=EOF)
{
memset(visit,0,sizeof(visit));
memset(mapp,0,sizeof(mapp));
for(i=0;i<m;i++)
{
scanf("%d%d",&x,&y);
mapp[x][y]=1;
mapp[y][x]=1;
}
flag=0;
dfs(1,1);
if(flag)
{
for(i=1;i<n;i++) printf("%d ",lu[i]);
printf("%d\n",lu[i]);
}
else printf("no solution\n");
}
return 0;
}
E题:HDU 4325 线段树
这道题hdu数据超水,达不到10^9,10^5数组标记就能过,那时候不会线段树,这是之前的代码
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string.h>
#include<ctype.h>
#include<stack>
#include<queue>
#include<set>
#include<algorithm>
#include <limits.h>
using namespace std;
int a[100005];
int main()
{
int t,n,m,i,j,s,e,k=1,x;
scanf("%d",&t);
while(t--)
{
memset(a,0,sizeof(a));
scanf("%d%d",&n,&m);
for(i=0;i<n;i++)
{
scanf("%d%d",&s,&e);
for(j=s;j<=e;j++)
a[j]++;
}
printf("Case #%d:\n",k++);
for(i=0;i<m;i++)
{
scanf("%d",&x);
printf("%d\n",a[x]);
}
}
return 0;
}
这是正确的做法:10^9树建不起来,需要用离散化,我想更加熟悉线段树就手敲了一发。我交题真的感觉没有任何问题,可是就是RE成狗,数组开小是T,数组开大就RE,超郁闷,最后根据网上的改自己的代码才AC,但是我依然没有发现我为何RE。还是觉得unique和lower_bound的离散化更加飘逸,我比较喜欢那种
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<map>
using namespace std;
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define MAXN 100100
int sum[MAXN<<2],cover[MAXN<<2];
int dat[MAXN*3];
int x[MAXN],y[MAXN];
int q[MAXN];
map<int,int> mp;
void pushdown(int rt){
if(cover[rt]){
cover[rt<<1] += cover[rt];
cover[rt<<1|1] += cover[rt];
sum[rt<<1] += cover[rt];
sum[rt<<1|1] += cover[rt];
cover[rt] = 0;
}
}
void build(int l,int r,int rt){
sum[rt] = 0;
cover[rt] = 0;
if(l==r) return ;
int m = (l+r)>>1;
build(lson);
build(rson);
}
void update(int L,int R,int l,int r,int rt){
if(L<=l&&r<=R){
cover[rt]++;
sum[rt]++;
return ;
}
pushdown(rt);
int m = (l+r)>>1;
if(L<=m) update(L,R,lson);
if(R>m) update(L,R,rson);
}
int query(int w,int l,int r,int rt){
if(l==r){
return sum[rt];
}
pushdown(rt);
int m = (l+r)>>1;
if(w<=m) return query(w,lson);
else return query(w,rson);
}
int main(){
int t,n,m,i,tot,k = 1;
scanf("%d",&t);
while(t--){
printf("Case #%d:\n",k++);
tot = 0;
scanf("%d%d",&n,&m);
for(i=1;i<=n;i++){
scanf("%d%d",&x[i],&y[i]);
dat[++tot] = x[i];
dat[++tot] = y[i];
}
for(i=1;i<=m;i++){
scanf("%d",&q[i]);
dat[++tot] = q[i];
}
sort(dat+1,dat+tot+1);
int cnt = 0;
dat[++cnt] = dat[1];
for(i=2;i<=tot;i++){
if(dat[i]!=dat[cnt]){
dat[++cnt] = dat[i];
}
}
build(1,cnt,1);
for(i=1;i<=cnt;i++){
mp[dat[i]] = i;
}
for(i=1;i<=n;i++){
update(mp[x[i]],mp[y[i]],1,cnt,1);
}
for(i=1;i<=m;i++){
printf("%d\n",query(mp[q[i]],1,cnt,1));
}
}
return 0;
}
F题: HDU 1231 最大连续子段和
方法很多
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string.h>
#include<ctype.h>
#include<stack>
#include<queue>
#include<set>
#include<algorithm>
#include <limits.h>
using namespace std;
int a[10005],x,y;
int maxsequence(int a[], int len)
{
int maxsum, maxhere;
int xx,yy;
xx=yy=x=y=a[0];
maxsum = maxhere =a[0];
for (int i=1; i<len; i++)
{
if (maxhere <= 0)
{
maxhere = a[i];
xx=yy=a[i];
}
else
{
maxhere += a[i];
yy=a[i];
}
if (maxhere > maxsum)
{
x=xx;
y=yy;
maxsum = maxhere;
}
}
return maxsum;
}
int main()
{
int k,i,maxm;
while(scanf("%d",&k),k)
{
for(i=0; i<k; i++)
scanf("%d",&a[i]);
maxm=maxsequence(a,k);
if(maxm<0)
printf("%d %d %d\n",0,a[0],a[k-1]);
else
printf("%d %d %d\n",maxm,x,y);
}
return 0;
}
G题:HDU 1412 水题
貌似题目本意是用STL去做
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<ctype.h>
#include<algorithm>
using namespace std;
int a[20005];
int main()
{
int n,m,i;
while(scanf("%d%d",&n,&m)!=EOF)
{
for(i=0;i<n+m;i++)
scanf("%d",&a[i]);
sort(a,a+n+m);
printf("%d",a[0]);
for(i=1;i<n+m;i++)
{
if(a[i]!=a[i-1])
printf(" %d",a[i]);
}
printf("\n");
}
return 0;
}
H题:POJ 2001 字典树
才学的,做了几道题,直接套模板
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string.h>
#include<ctype.h>
#include<stack>
#include<queue>
#include<set>
#include<algorithm>
#include <limits.h>
#define PI acos(-1)
#define MAX 26
using namespace std;
char str[1005][25];
typedef struct Trie
{
Trie *next[MAX];
int v; //根据需要变化
};
Trie root;
void createTrie(char *str)
{
int len = strlen(str);
Trie *p =&root, *q;
for(int i=0; i<len; ++i)
{
int id = str[i]-'a';
if(p->next[id] == NULL)
{
q = new Trie;
q->v = 0;
for(int j=0; j<MAX; ++j)
q->next[j] = NULL;
p->next[id] = q;
}
p->next[id]->v++;
p = p->next[id];
}
}
void findTrie(char *str)
{
int len = strlen(str);
Trie *p =&root;
for(int i=0; i<len; ++i)
{
int id = str[i]-'a';
p=p->next[id];
printf("%c",str[i]);
if(p->v==1) break;
}
printf("\n");
}
int main()
{
int i,n=0;
while(scanf("%s",str[n])!=EOF)
{
createTrie(str[n++]);
}
for(i=0;i<n;i++)
{
printf("%s ",str[i]);
findTrie(str[i]);
}
return 0;
}
I题: POJ 3041 二分图匹配
也是才学的,模板题
#include<cstdio>
#include<iostream>
#include<cmath>
#include<cstring>
#include<string.h>
#include<ctype.h>
#include<stack>
#include<queue>
#include<set>
#include<algorithm>
#include<limits.h>
#define PI acos(-1)
using namespace std;
bool mapp[505][505];
bool visit[505];
int link[505];
int n;
bool find(int v)
{
int i;
for(i=1; i<=n; i++)
{
if(mapp[v][i]&&!visit[i])
{
visit[i]=true;
if(link[i]==0||find(link[i]))
{
link[i]=v;
return true;
}
}
}
return false;
}
int main()
{
int k,i,x,y,ans=0;
scanf("%d%d",&n,&k);
for(i=0;i<k;i++)
{
scanf("%d%d",&x,&y);
mapp[x][y]=true;
}
for(i=1; i<=n; i++)
{
memset(visit,0,sizeof(visit));
if(find(i)) ans++;
}
printf("%d\n",ans);
return 0;
}
小结:这次周赛卡题了,我第一眼看到第三题标题是中文就点开了,结果被卡了很久,浪费了很多时间,不然应该还能做出A题和D题。卡题对心情影响挺大的,想做出来又觉得耽误了很多时间,不做出来又不甘心,有点蛋疼