uva 658 UVA 658 It's not a Bug, it's a Feature!

来源:互联网 发布:网络交易管理办法 pdf 编辑:程序博客网 时间:2024/05/20 05:55

本题有两大难点,一是建图。其实无论邻接表还是邻接矩阵貌似建完整图的时间复杂度都比较大,而且好多状态未必用的到,因而不如干脆不建完整图,每次都扫描一遍转换规则,如果可以生成另一个状态就将另一个状态直接入队即可。状态可以用二进制表示。

二是判断当前状态,用二进制来判断。

  ①判定某些位置是否为1,如判定2、4位置为1,则转化为判断x|0101是否等于x。

    ②判定某些位置是否为0,如判定2、4位置为0,则转化为判断x&1010是否等于x。

    ③将某些位置转化为1,如2、4位置转化为1,则令x=x|0101。

    ④将某些位置转化为0,如2、4位置转化为0,则令x=x&1010。

//  Created by Chenhongwei in 2015.//  Copyright (c) 2015 Chenhongwei. All rights reserved.#include "iostream"#include "cstdio"#include "cstdlib"#include "cstring"#include "climits"#include "queue"#include "cmath"#include "map"#include "set"#include "stack"#include "vector"#include "sstream"#include "algorithm"using namespace std;const int inf=1e9;const int maxn=(2<<20)+100;typedef long long ll;bool vis[maxn];int d[maxn];int  b[2][150],a[2][150];int n,m;int w[150];void SPFA(){memset(vis,0,sizeof vis);memset(d,0x3f,sizeof d);int inti=(1<<n)-1;queue<int >q;q.push(inti);d[inti]=0;vis[inti]=1;while(!q.empty()){int u=q.front();q.pop();// cout<<u<<endl;vis[u]=0;for(int i=1;i<=m;i++)if((u&b[1][i])==u&&(u|b[0][i])==u){int v=u;v|=a[0][i];v&=a[1][i];if(d[v]>d[u]+w[i]){d[v]=d[u]+w[i];if(!vis[v]){vis[v]=1;q.push(v);}}}}if(d[0]>inf)cout<<"Bugs cannot be fixed."<<endl<<endl;else cout<<"Fastest sequence takes "<<d[0]<<" seconds."<<endl<<endl;}int main(){//ios::sync_with_stdio(false);// freopen("in.txt","r",stdin);//freopen("out.txt","w",stdout);int kase=0;while(scanf("%d%d",&n,&m)&&(n+m)){printf("Product %d\n",++kase);char s[150],t[150];memset(a,0,sizeof a);memset(b,0,sizeof b);for(int i=1;i<=m;i++){scanf("%d%s%s",&w[i],s,t);for(int j=0;j<n;j++){if(s[j]=='+')b[0][i]+=(1<<j);if(s[j]!='-')b[1][i]+=(1<<j);if(t[j]=='+')a[0][i]+=(1<<j);if(t[j]!='-')a[1][i]+=(1<<j);}// cout<<b[0][i]<<' '<<b[1][i]<<' '<<a[0][i]<<' '<<a[1][i]<<endl;}SPFA();}return 0;}


0 0
原创粉丝点击