• poj 3249(bfs+dp或者记忆化搜索)


    题目链接:http://poj.org/problem?id=3249

    思路:dp[i]表示到点i的最大收益,初始化为-inf,然后从入度为0点开始bfs就可以了,一开始一直TLE,然后优化了好久才4000ms险过。

    之后有写了个dfs记忆化搜索,果然快多了。

    bfs AC code:

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 #include<queue>
     6 using namespace std;
     7 #define MAXN 100100
     8 #define MAXM 2002000
     9 #define inf 1<<30
    10 
    11 struct Edge{
    12     int v,next;
    13 }edge[MAXM];
    14 
    15 int n,m,NE;
    16 int head[MAXN];
    17 
    18 void Insert(int u,int v)
    19 {
    20     edge[NE].v=v;
    21     edge[NE].next=head[u];
    22     head[u]=NE++;
    23 }
    24 
    25 int In_degree[MAXN],Out_degree[MAXN];
    26 int dp[MAXN],value[MAXN];
    27 bool mark[MAXN];
    28 
    29 void bfs()
    30 {
    31     queue<int>que;
    32     fill(dp,dp+1+n,-inf);
    33     memset(mark,false,(n+2)*sizeof(bool));
    34     for(int i=1;i<=n;i++)if(In_degree[i]==0){
    35         mark[i]=true;
    36         dp[i]=value[i];
    37         que.push(i);
    38     }
    39     while(!que.empty()){
    40         int u=que.front();
    41         que.pop();
    42         mark[u]=false;
    43         for(int i=head[u];i!=-1;i=edge[i].next){
    44             int v=edge[i].v;
    45             if(dp[u]+value[v]>dp[v]){
    46                 dp[v]=dp[u]+value[v];
    47                 if(!mark[v]){
    48                     mark[v]=true;que.push(v);
    49                 }
    50             }
    51         }
    52     }
    53 }
    54 
    55 
    56 int main()
    57 {
    58     int u,v,ans;
    59     while(~scanf("%d%d",&n,&m)){
    60         NE=0;
    61         memset(head,-1,(n+2)*sizeof(int));
    62         memset(In_degree,0,(n+2)*sizeof(int));
    63         memset(Out_degree,0,(n+2)*sizeof(int));
    64         for(int i=1;i<=n;i++)scanf("%d",&value[i]);
    65         while(m--){
    66             scanf("%d%d",&u,&v);
    67             Insert(v,u);
    68             In_degree[u]++;
    69             Out_degree[v]++;
    70         }
    71         bfs();
    72         ans=-inf;
    73         for(int i=1;i<=n;i++){
    74             if(Out_degree[i]==0)ans=max(ans,dp[i]);
    75         }
    76         printf("%d
    ",ans);
    77     }
    78     return 0;
    79 }
    View Code

    dfs 记忆化 AC code:

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 #include<queue>
     6 using namespace std;
     7 #define MAXN 100100
     8 #define MAXM 2002000
     9 #define inf 1<<30
    10 
    11 struct Edge{
    12     int v,next;
    13 }edge[MAXM];
    14 
    15 int n,m,NE;
    16 int head[MAXN];
    17 
    18 void Insert(int u,int v)
    19 {
    20     edge[NE].v=v;
    21     edge[NE].next=head[u];
    22     head[u]=NE++;
    23 }
    24 
    25 int In_degree[MAXN],Out_degree[MAXN];
    26 int dp[MAXN],value[MAXN];
    27 
    28 int dfs(int u)
    29 {
    30     if(dp[u]!=-inf)return dp[u];
    31     dp[u]=value[u];
    32     int ans=-inf;
    33     for(int i=head[u];i!=-1;i=edge[i].next){
    34         int v=edge[i].v;
    35         ans=max(ans,dfs(v));
    36     }
    37     if(ans!=-inf){
    38         dp[u]+=ans;
    39     }
    40     return dp[u];
    41 }
    42 
    43 int main()
    44 {
    45     int u,v,ans;
    46     while(~scanf("%d%d",&n,&m)){
    47         NE=0;
    48         memset(head,-1,(n+2)*sizeof(int));
    49         memset(In_degree,0,(n+2)*sizeof(int));
    50         memset(Out_degree,0,(n+2)*sizeof(int));
    51         for(int i=1;i<=n;i++)scanf("%d",&value[i]);
    52         while(m--){
    53             scanf("%d%d",&u,&v);
    54             Insert(u,v);
    55             In_degree[v]++;
    56             Out_degree[u]++;
    57         }
    58         ans=-inf;
    59         fill(dp,dp+1+n,-inf);
    60         for(int i=1;i<=n;i++){
    61             if(In_degree[i]==0){
    62                 ans=max(ans,dfs(i));
    63             }
    64         }
    65         printf("%d
    ",ans);
    66     }
    67     return 0;
    68 }
    View Code
  • 相关阅读:
    码农如何通过编程赚更多的钱
    理解 OAuth 2.0 认证流程
    把同事的代码重写得干净又整洁,老板却让我做回滚?
    精读《如何做好 CodeReview》
    互联网行业的软件与人员的代际更迭随想
    十大最佳自动化测试工具
    使用 docker 高效部署你的前端应用
    在Linux 命令行中转换大小写
    Python批量检测服务器端口可用性与Socket函数使用
    基于华为云CSE微服务接口兼容常见问题
  • 原文地址:https://www.cnblogs.com/wally/p/3282193.html
Copyright © 2020-2023  润新知