zoukankan      html  css  js  c++  java
  • BZOJ3436 小K的农场

    Description

    背景
    小K是个特么喜欢玩MC的孩纸。。。
    描述
    小K在MC里面建立很多很多的农场,总共n个,以至于他自己都忘记了每个农场中种植作物的具体数量了,他只记得
    一些含糊的信息(共m个),以下列三种形式描述:农场a比农场b至少多种植了c个单位的作物,农场a比农场b至多
    多种植了c个单位的作物,农场a与农场b种植的作物数一样多。但是,由于小K的记忆有些偏差,所以他想要知道存
    不存在一种情况,使得农场的种植作物数量与他记忆中的所有信息吻合。

    Input

    第一行包括两个整数n和m,分别表示农场数目和小K记忆中的信息的数目接下来m行:如果每行的第一个数是1,接
    下来有三个整数a,b,c,表示农场a比农场b至少多种植了c个单位的作物如果每行第一个数是2,接下来有三个整数a
    ,b,c,表示农场a比农场b至多多种植了c个单位的作物如果每行第一个数是3,接下来有两个整数a,b,表示农场a
    种植的数量与b一样。1<=n,m,a,b,c<=10000

    Output

    如果存在某种情况与小K的记忆吻合,输出”Yes”,否则输出”No”

    Sample Input

    3 3
    3 1 2
    1 1 3 1
    2 2 3 2

    Sample Output

    Yes
    样例解释
    三个农场种植的数量可以为(2,2,1)

    HINT

    Source

    Kpmcup#0 By Greens

    正解:差分约束系统

    解题报告:

      这道题就是一道差分约束系统裸题。

      好久没做差分约束系统的题我都快忘了怎么连边了...首先如果x-y<=z,那么显然y的值到x的值必须要把差控制在z以内,所以应该是y向x连边,边权为z;如果是x-y>=z,那么,显然是转成y-x<=-z,所以x向y连一条-z的边(一般都习惯以小于号为主体)。所以我们只要找负权环就可以了。

      相等的时候并不用考虑,直接连一条边权为0的边即可,一条两条随意。

      当然,找负权环,dfs版SPFA肯定要优秀一些。

     1 //It is made by jump~
     2 #include <iostream>
     3 #include <cstdlib>
     4 #include <cstring>
     5 #include <cstdio>
     6 #include <cmath>
     7 #include <algorithm>
     8 #include <ctime>
     9 #include <vector>
    10 #include <queue>
    11 #include <map>
    12 #include <set>
    13 using namespace std;
    14 typedef long long LL;
    15 const int MAXN = 10011;
    16 const int MAXM = 20011;
    17 int n,m,ecnt,top;
    18 int first[MAXN],to[MAXM],next[MAXM],w[MAXM],dis[MAXN];
    19 int stack[MAXN],cnt[MAXN];
    20 bool in[MAXN];
    21 
    22 inline int getint()
    23 {
    24     int w=0,q=0; char c=getchar();
    25     while((c<'0' || c>'9') && c!='-') c=getchar(); if(c=='-') q=1,c=getchar(); 
    26     while (c>='0' && c<='9') w=w*10+c-'0', c=getchar(); return q ? -w : w;
    27 }
    28 inline void link(int x,int y,int z){ next[++ecnt]=first[x]; first[x]=ecnt; to[ecnt]=y; w[ecnt]=z; }
    29 inline bool SPFA(){ 
    30     for(int i=1;i<=n;i++) dis[i]=0,stack[++top]=i,in[i]=1;
    31     int u;
    32     while(top>0) {
    33     u=stack[top]; top--; in[u]=0;
    34     for(int i=first[u];i;i=next[i]) {
    35         int v=to[i]; 
    36         if(dis[v]>dis[u]+w[i]) {
    37         dis[v]=dis[u]+w[i];
    38         if(!in[v]) { in[v]=1; stack[++top]=v; cnt[v]++; if(cnt[v]>=n) return false;}
    39         }
    40     }
    41     }
    42     return true;
    43 }
    44 
    45 inline void work(){
    46     n=getint(); m=getint(); int x,y,z,ljh;
    47     for(int i=1;i<=m;i++) {
    48     ljh=getint(); x=getint(); y=getint();
    49     if(ljh==1) z=getint(),link(x,y,-z);
    50     else if(ljh==2) z=getint(),link(y,x,z);
    51     else link(x,y,0);
    52     }
    53     if(SPFA()) printf("Yes"); else printf("No");
    54 }
    55 
    56 int main()
    57 {
    58     work();
    59     return 0;
    60 }
  • 相关阅读:
    c++构造函数析构函数调用顺序
    c++隐藏实例
    c++子类和父类成员函数重名
    C++虚函数·
    c/c++字符数组和字符串大揭秘
    python 基础回顾 一
    python java scala 单例模式
    推荐一款好用并且免费的markdown软件 Typora
    java 的垃圾回收机制 【转】
    python的垃圾回收机制【转】
  • 原文地址:https://www.cnblogs.com/ljh2000-jump/p/5905520.html
Copyright © 2011-2022 走看看