2018.7.5 模拟赛

这次比赛再一次确认了我是瞎子的事实。。。。。
盲人。

T1,一道曾经讲过的原题,忘了原来做法,写了个二分+spfa。结果手残打出了以下代码

    if(c>='a' && c<='z') x=c-70,city[x]=2;
    if(s>='a' && s<='z') y=s-70,city[x]=2;

两个x真的是棒,结果样例还过了????手造数据还过了?????假的吧。
这种错误不只一次犯了, 以后每次写完代码一定要检查,养成好习惯。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<queue>

using namespace std;
const int MAXN = 3005;

int n,p,sum,S,T,ans,num;
int head[MAXN],cnt;
int to[MAXN<<1],nxt[MAXN<<1];
int city[MAXN],dis[MAXN];
bool vis[MAXN];

inline void add(int bg,int ed){
    to[++cnt]=ed,nxt[cnt]=head[bg],head[bg]=cnt;
}

inline bool check(int x){
    memset(vis,0,sizeof(vis));
    memset(dis,-1,sizeof(dis));
    queue<int> q;
    q.push(S);vis[S]=1;dis[S]=x;    
    while(q.size()){
        int xx=q.front();q.pop();
        vis[xx]=0;
        for(register int i=head[xx];i;i=nxt[i]){
            int u=to[i];
            if(city[u]==1){
                int now=0;
                now=dis[xx]/20;
                if(now*20<dis[xx]) now++;
//              if(dis[xx]-now<x) continue;
                if(dis[u]<dis[xx]-now){
                    dis[u]=dis[xx]-now;
                    if(!vis[u]) {
                        vis[u]=1;
                        q.push(u);
                    }
                }
            }
            else{
                if(dis[u]<dis[xx]-1){
//                  if(dis[xx]-1<x) continue;
                    dis[u]=dis[xx]-1;
                    if(!vis[u])
                        vis[u]=1;
                        q.push(u);
                }
            }
//          if(u==T) return true;
        }
    }
    if(dis[T]>=sum) return true;
    return false;
}

int main(){
    freopen("toll.in","r",stdin);
    freopen("toll.out","w",stdout); 
    while(~scanf("%d",&n)){
        num++;
        if(n==-1) break;
        ans=0;cnt=0;
        memset(head,0,sizeof(head));
        memset(city,0,sizeof(city));
        for(register int i=1;i<=n;i++){
            char c,s;
            int x,y;
            cin>>c>>s;
            if(c>='A' && c<='Z') x=c-'A'+1,city[x]=1;
            if(s>='A' && s<='Z') y=s-'A'+1,city[y]=1; 
            if(c>='a' && c<='z') x=c-70,city[x]=2;
            if(s>='a' && s<='z') y=s-70,city[y]=2;
            add(x,y);add(y,x);
    //      cout<<x<<" "<<y<<endl;
        }
        char c,s;
        scanf("%d",&sum);
        cin>>c>>s;
        if(c>='A' && c<='Z') S=c-'A'+1;
        if(s>='A' && s<='Z') T=s-'A'+1;
        if(c>='a' && c<='z') S=c-70;
        if(s>='a' && s<='z') T=s-70;
        int l=sum,r=100000000;
        while(l<=r){
            int mid=l+r>>1;
            if(check(mid)) {
                ans=mid;
                r=mid-1;
            }
            else 
                l=mid+1;
        }
        printf("Case %d: %d\n",num,ans);
    }
    return 0;
}

T2看了半天题,结果没看懂,自己yy了一道题来做???并查集,我是来搞笑的。
正解结果是一个lis,虽然看出了点门道没多想。爆零GG。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<algorithm>

using namespace std;
const int MAXN = 100005;

int n;
int a[MAXN],dp[MAXN];
int top;

int main(){ 
    freopen("sort.in","r",stdin);
    freopen("sort.out","w",stdout);
    scanf("%d",&n);
    for(register int i=1;i<=n;i++) scanf("%d",&a[i]);
    for(register int i=1;i<=n;i++)  {
        if(dp[top]<a[i]) dp[++top]=a[i];
        else dp[lower_bound(dp+1,dp+1+top,a[i])-dp]=a[i];
    }
    printf("%d",top);
}

T3 刚开始写状压,后面认为自己状压太丑就写了一发爆搜+剪枝。一个最优性剪枝是记录下来后面还能打开的最大的钥匙的量,如果加上现在的还是小于答案就直接跳。结果。。。刚开始错误的一个剪枝没删干净?????还给了60????

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<cstdlib>
#include<algorithm>

using namespace std;
const int MAXN = 20;

int n,A,B,C;
int ans,ret;
bool vis[MAXN];

struct Door{
    int use[5],sum,key[5];
}door[MAXN];

//inline bool cmp(Door A,Door B){
//  return A.sum<B.sum;
//}

inline int rd(){
    int x=0,f=1;char ch=getchar();
    while(!isdigit(ch)) {if(ch=='-') f=-1;ch=getchar();}
    while(isdigit(ch)) {x=(x<<1)+(x<<3)+ch-48;ch=getchar();}
    return x*f;
}

inline void dfs(int u,int x,int y,int z){
    if(x+y+z>ans) ans=x+y+z;
    if(x+y+z+ret<=ans) return;
//  if(x+y+z<door[u].sum) return;
//  if(u==n+1) return;
    for(register int i=1;i<=n;i++){
        if(vis[i]) continue;

        if(x>=door[i].use[1] && y>=door[i].use[2]){
            vis[i]=1;
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret+door[i].sum-door[i].key[2]-door[i].key[1]-door[i].key[3];
            dfs(i,x-door[i].use[1]+door[i].key[1],y-door[i].use[2]+door[i].key[2],z+door[i].key[3]);
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret-door[i].sum+door[i].key[2]+door[i].key[1]+door[i].key[3];
            vis[i]=0;
        }
        if(x>=door[i].use[1] && y<door[i].use[2] && y+z>=door[i].use[2]){
            vis[i]=1;
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret+door[i].sum-door[i].key[2]-door[i].key[1]-door[i].key[3];
            dfs(i,x-door[i].use[1]+door[i].key[1],door[i].key[2],z-(door[i].use[2]-y)+door[i].key[3]);
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret-door[i].sum+door[i].key[2]+door[i].key[1]+door[i].key[3];
            vis[i]=0;
        }
        if(y>=door[i].use[2] && x<door[i].use[1] && x+z>=door[i].use[1]){
            vis[i]=1;
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret+door[i].sum-door[i].key[2]-door[i].key[1]-door[i].key[3];
            dfs(i,door[i].key[1],y-door[i].use[2]+door[i].key[2],z-(door[i].use[1]-x)+door[i].key[3]);
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret-door[i].sum+door[i].key[2]+door[i].key[1]+door[i].key[3];
            vis[i]=0;
        }
        if(y<door[i].use[2] && x<door[i].use[1] && (x+y+z)>=door[i].sum){
            vis[i]=1;
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret+door[i].sum-door[i].key[2]-door[i].key[1]-door[i].key[3];
            dfs(i,door[i].key[1],door[i].key[2],x+y+z-door[i].sum+door[i].key[3]);
            if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
                ret=ret-door[i].sum+door[i].key[2]+door[i].key[1]+door[i].key[3];
            vis[i]=0;
        }
//      dfs(i,x,y,z);   
//      vis[i]=0;
    }
}

int main(){
    freopen("room.in","r",stdin);
    freopen("room.out","w",stdout);
    n=rd();
    for(register int i=1;i<=n;i++) door[i].use[1]=rd();
    for(register int i=1;i<=n;i++) door[i].use[2]=rd();
    for(register int i=1;i<=n;i++) door[i].key[1]=rd();
    for(register int i=1;i<=n;i++) door[i].key[2]=rd();
    for(register int i=1;i<=n;i++) door[i].key[3]=rd();
    A=rd();B=rd();C=rd();
    for(register int i=1;i<=n;i++)
        door[i].sum=door[i].use[1]+door[i].use[2];
//  cout<<ret<<endl;
//  sort(door+1,door+1+n,cmp);
//  for(register int i=1;i<=n;i++) cout<<door[i].sum<<" ";
//  cout<<endl;
//  cout<<ret<<endl;
//  for(register int i=2;i<=n;i++)
//      ret[i]=ret[i-1]+door[i-1].sum-door[i-1].key[1]-door[i-1].key[2]-door[i-1].key[3];
//  for(register int i=1;i<=n;i++)
//      cout<<ret[i]<<" ";
//  cout<<endl;
    for(register int i=1;i<=n;i++)
        if(door[i].key[1]+door[i].key[2]+door[i].key[3]>door[i].sum)
            ret+=door[i].key[1]+door[i].key[2]+door[i].key[3]-door[i].sum;
    dfs(1,A,B,C);
    printf("%d",ans);
    return 0;
}

总结:
这次考试真的的是菜成狗,首要问题是治眼瞎和脑残,以后写完代码都要检查一遍,都要自己造数据争取1A。。好的,就这样吧。

posted @ 2018-07-05 16:05  Monster_Qi  阅读(108)  评论(0编辑  收藏  举报