POJ 3249 Test for Job(记忆化搜索)

题意:

给你一个有向图,每一个节点有一个权值,现在要你从一个入度为0 到一个出度为0的路径,使得权值最大。

思路:

1. 建立反图,于是问题比较清晰:<已知出发状态,未知值> 然后根据边进行记忆化搜索。

2. http://www.cnblogs.com/kedebug/archive/2013/04/07/3006515.html 以前有过总结,用到本题上要保证图是单向的。

 

#include <iostream>

#include <vector>

#include <stack>

#include <algorithm>

using namespace std;



const int MAXN = 100010;

const int INFS = 0x7FFFFFFF;



vector<int> G[MAXN];

int F[MAXN], val[MAXN], indeg[MAXN];



int dp(int u) {

    if (F[u] != -INFS) 

        return F[u];



    F[u] = val[u];

    int ans = -INFS;

    for (int i = 0; i < G[u].size(); i++) {

        int v = G[u][i];

        ans = max(ans, dp(v));

    }

    if (ans != -INFS)

        F[u] += ans;

    return F[u];

}



int main() {

    int n, m;

    while (~scanf("%d%d", &n, &m)) {

        for (int i = 1; i <= n; i++) {

            scanf("%d", &val[i]);

            G[i].clear();

            F[i] = -INFS, indeg[i] = 0;

        }

        while (m--) {

            int u, v;

            scanf("%d%d", &u, &v);

            G[v].push_back(u);

            indeg[u] += 1;

        }

        int ans = -INFS;

        for (int i = 1; i <= n; i++)

            if (!indeg[i]) 

                ans = max(ans, dp(i));

        printf("%d\n", ans);

    }

    return 0;

}

你可能感兴趣的:(test)