題目鏈結
一條街的一邊有幾座房子,因為環保原因居民想要在路邊種些樹。
路邊的地區被分割成塊,並被編號成 1,2,…,n。每個部分為乙個單位尺寸大小並最多可種一棵樹。
每個居民都想在門前種些樹,並指定了三個號碼 b,e,t。這三個數表示該居民想在地區 b 和 e 之間(包括 b 和 e)種至少 t 棵樹。
居民們想種樹的各自區域可以交叉。你的任務是求出能滿足所有要求的最少的樹的數量。
輸入的第一行是乙個整數,代表區域的個數 n。
輸入的第二行是乙個整數,代表房子個數 h。
第 3 到第 (h + 2) 行,每行三個整數,第 (i + 2) 行的整數依次為 bi,ei,ti,代表第 i 個居民想在 bi 和 ei 之間種至少 ti 棵樹。
輸出一行乙個整數,代表最少的樹木個數。輸入9
41 4 2
4 6 2
8 9 2
3 5 2
輸出資料規模與約定
對於 100% 的資料,保證:
1 ≤ n ≤ 3 × 104,1 ≤ h ≤ 5 × 103。
1 ≤ bi ≤ ei ≤ n,1 ≤ ti ≤ ei - bi + 1。
sum[e] - sum[b - 1] ≥ t,則 sum[b - 1] ≤ sum[e] - t,那麼 e 到 b - 1 就可以連一條權值為 -t 的邊,而 0 ≤ sum[i] - sum[i - 1] ≤ 1,則 sum[i-1] ≤ sum[i],sum[i] ≤ sum[i - 1] + 1,那麼 i 到 i - 1 就可以連一條權值為 0 的邊,i - 1 到 i 就可以連一條權值為 1 的邊,然後用 spfa 跑最短路即可。
#include
using
namespace std;
const
int n=
50000
;const
int inf=
0x3f3f3f3f
;int dis[n]
,n,m;
bool vis[n]
;struct edgee[n*2]
;int h[n]
,tot=0;
void
add(
int u,
int v,
int w)
void
spfa
(int k)}}
}}intmain()
int b,e,t;
for(
int i=
0;i)for
(int i=
1;i<=n;i++
)spfa
(s);
printf
("%d\n"
,-dis[0]
);return0;
}
種樹(差分約束)
種樹 來自 luogu 1250 題目概述 一條街的一邊有幾座房子。因為環保原因居民想要在路邊種些樹。路邊的地區被分割成塊,並被編號成1.n。每個部分為乙個單位尺寸大小並最多可種一棵樹。每個居民想在門前種些樹並指定了三個號碼b,e,t。這三個數表示該居民想在b和e之間最少種t棵樹。當然,b e,居民...
種樹 差分約束 貪心
先看貪心版本。每次種的樹在重疊區間越多,種的樹越少。只有結束位置才會重合,就對區間結束的位置從小到大排序。然後遍歷每個區間統計第i個區間種了k個樹,若k大於 t 則continue,否則從區間末尾往前種樹。貪心種樹 include using namespace std struct n print...
種樹(一道簡單的差分約束系統)
為了綠化鄉村,h村積極響應號召,開始種樹了。h村里有n幢房屋,這些屋子的排列順序很有特點,在一條直線上。於是方便起見,我們給它們標上1 n。樹就種在房子前面的空地上。同時,村民們向村長提出了m個意見,每個意見都是按如下格式 希望第li個房子到第ri個房子的房前至少有ci棵樹。因為每個房屋前的空地面積...