• HDU 1384 Intervals(差分约束)


    题意:给你n个区间,然后你需要在区间中选取最少c个,这c个数存在于集合z中,问你集合z最少有多少个元素

    思路:刚接触差分约束,感觉是一种套路,不过差分约束的模型的确不容易看出来(先感谢聚聚博客中对于差分约束的讲解,传送门),感觉讲的很清楚,对于最小值,找最长路,最大值最短路(可能这就是使用spfa的唯一道路,逃)

    代码:

    #include <bits/stdc++.h>
    using namespace std;
    typedef long long LL;
    inline LL read()
    {
        LL x=0,f=1;char ch=getchar();
        while(ch>'9'||ch<'0'){if(ch=='-')f=-1;ch=getchar();}
        while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
        return x*f;
    }
    
    const int MAXN=50005;
    const int INF=-0x3f3f3f3f;
    int n,m,ans;
    int head[MAXN];
    //int begin1,end1;
    int dis[MAXN],vis[MAXN];
    
    struct node
    {
        int u,v,w;
        int next;
    }edge[MAXN<<2];
    void init()
    {
        ans=0;
        memset(head,-1,sizeof(head));
    }
    void add(int u,int v,int w)
    {
        edge[ans].u=u;
        edge[ans].v=v;
        edge[ans].w=w;
        edge[ans].next=head[u]; // next标记以u为起点的下一条边
        head[u]=ans++; // head标记这个点是哪条边的起点,更新head
    }
    
    void SPFA(int begin1,int end1)
    {
        int i,j;
        queue<int>q;
    //    for(int i=0;i<n;i++) dis[i]=INF;
        memset(dis,-0x3f,sizeof(dis));
        memset(vis,0,sizeof(vis));
        dis[begin1]=0,vis[begin1]=1;
    
        q.push(begin1);
        while(!q.empty()){
            int u=q.front();
            q.pop();
    //        printf("trst %d
    ",u);
            vis[u]=0;
            for(i=head[u];i!=-1;i=edge[i].next){
                int top=edge[i].v;
                if(dis[top]<dis[u]+edge[i].w){
                    dis[top]=dis[u]+edge[i].w;
                    if(!vis[top]){
                        vis[top]=1;
                        q.push(top);
                    }
                }
            }
        }
    //    if(dis[end1]==INF) printf("-1
    ");
    //    else printf("%d
    ",dis[end1]);
    }
    
    int main()
    {
        while(~scanf("%d",&n)){
            int s=999999,t=0;
            init();
            for(int i=1;i<=n;i++){
                int u=read(),v=read(),w=read();
                add(u,v+1,w);
                s=min(s,u);
                t=max(t,v+1);
            }
            for(int i=s;i<t;i++)add(i,i+1,0),add(i+1,i,-1);
            SPFA(s,t);
            printf("%d
    ",dis[t]);
        }
        return 0;
    }
  • 相关阅读:
    第36课 经典问题解析三
    第35课 函数对象分析
    67. Add Binary
    66. Plus One
    58. Length of Last Word
    53. Maximum Subarray
    38. Count and Say
    35. Search Insert Position
    28. Implement strStr()
    27. Remove Element
  • 原文地址:https://www.cnblogs.com/lalalatianlalu/p/9811419.html
Copyright © 2020-2023  润新知