状态转移的最短路 隐式图搜索 UVA 658

Posted 不知姓名的黑猫君

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了状态转移的最短路 隐式图搜索 UVA 658相关的知识,希望对你有一定的参考价值。

紫书365

题目大意:给你n个全都是bug的东西,然后每次可以修复,给你修复前后的状态,问最后如果能把bug全都修复,最少需要多少时间。

思路:从最初状态开始,然后枚举bug即可。

表示priority里面的bool operator和单纯的sort的定义的大小于号是不一样的啊,如果你想用sort来计算struct从小到大的的话是这样的

技术分享
struct Node{
    int bugs, dist;
    bool operator < (const Node &a) const{
        return dist < a.dist;
    }
    Node(int b = 0, int d = 0): bugs(b), dist(d){}
};
View Code

而优先队列是这样的

技术分享
struct Node{
    int bugs, dist;
    bool operator < (const Node &a) const{
        return dist > a.dist;
    }
    Node(int b = 0, int d = 0): bugs(b), dist(d){}
};
View Code

区分一下大小于号就好了

技术分享
//看看会不会爆int!数组会不会少了一维!
//取物问题一定要小心先手胜利的条件
#include <bits/stdc++.h>
using namespace std;
#define LL long long
#define ALL(a) a.begin(), a.end()
#define pb push_back
#define mk make_pair
#define fi first
#define se second
const int inf = 0x3f3f3f3f;
const int maxn = (1 << 20) + 5;
const int maxm = 100 + 5;
int n, m;
int t[maxm], d[maxn];
bool vis[maxn];
char b[maxm][30], e[maxm][30];
struct Node{
    int bugs, dist;
    bool operator < (const Node &a) const{
        return dist > a.dist;
    }
    Node(int b = 0, int d = 0): bugs(b), dist(d){}
};

int solve(){
    memset(vis, false, sizeof(vis));
    memset(d, 0x3f, sizeof(d));
    priority_queue<Node> que;
    int tmp = (1 << n) - 1;
    que.push(Node(tmp, 0));
    d[tmp] = 0; vis[tmp] = 1;
    while (!que.empty()){
        Node u = que.top(); que.pop();
        if (u.bugs == 0) return u.dist;
        for (int i = 0; i < m; i++){
            int from = u.bugs;
            bool flag = false;
            for (int j = 0; j < n; j++){
                if (b[i][j] == - && (from & (1 << j))) {flag = true; break;}
                if (b[i][j] == + && !(from & (1 << j))) {flag = true; break;}
            }
            if (flag) continue;
            int to = from;
            for (int j = 0; j < n; j++){
                if (e[i][j] == - && (from & (1 << j))) to ^= 1 << j;
                if (e[i][j] == +) to |= 1 << j;
            }
            if (d[to] > d[from] + t[i] && !vis[to]){
                d[to] = d[from] + t[i];
                vis[to] = false;
                que.push(Node(to, d[to]));
            }
        }
    }
    return -1;
}

int main(){
    int kase = 0;
    while (scanf("%d%d", &n, &m) && n){
        for (int i = 0; i < m; i++){
            scanf("%d", t + i);
            scanf("%s%s", b[i], e[i]);
        }
        printf("Product %d\n", ++kase);
        int ans = solve();
        if (ans < 0) printf("Bugs cannot be fixed.\n");
        else printf("Fastest sequence takes %d seconds.\n", ans);
        printf("\n");
    }
    return 0;
}
View Code

 

以上是关于状态转移的最短路 隐式图搜索 UVA 658的主要内容,如果未能解决你的问题,请参考以下文章

UVa658 It's not a Bug, it's a Feature! (最短路,隐式图搜索)

uva658 It's not a Bug, it's a Feature!

UVa 658 - It's not a Bug, it's a Feature!(Dijkstra + 隐式图搜索)

UVa10603 Fill (隐式图搜索+Dijkstra)

uva-321-暴力枚举-隐式图搜索

路径寻找(隐式图遍历)