區間選點 差分約束系統問題

2021-10-05 03:28:25 字數 2070 閱讀 2980

給定乙個數軸上的 n 個區間,要求在數軸上選取最少的點使得第 i 個區間 [ai, bi] 裡至少有 ci 個點。

輸入第一行乙個整數 n 表示區間的個數,接下來的 n 行,每一行兩個用空格隔開的整數 a,b 表示區間的左右端點。1 <= n <= 50000, 0 <= ai <= bi <= 50000 並且 1 <= ci <= bi - ai+1。

輸出乙個整數表示最少選取的點的個數

537

38103

6811

311011

1

6
使用差分約束系統的思路

關於差分約束的幾個解釋

②關於解的存在性

1.存在負環(正環) 分別對應跑最短路和最長路

不等式約束上表現為xi-x1<=t t為無窮小(舉個例子,x1-1<=x2 , x2-1<=x1越跑越小)

2.終點不可達

表明xi與x1之間沒有約束條件,對應**中dis[i]=inf.

③關於跑最長路還是最短路???

1.如果差分約束系統是<=則跑最短路

2.相反差分約束系統是》=則跑最長路

這是因為要滿足多個不等式約束,所以跑最短路得到的是上界(最大解)。

跑最長路得到的是下界(最小解)。

對於本題

構造差分約束系統不等式如下:(求最小值跑最長路)

因為本題資料保證一定有解,所以不需要判斷正環。

如果要判斷正環的話,要注意 本題給的n是區間的個數,而不是等價為圖之後點的個數。

點的個數為themax - themin +

;//鏈式前向星

struct edge

edge[maxm]

;int head[maxn]

,cnt;

void

init()

void

add(

int u,

int v,

int w)

//spfa

int vis[maxn]

,cn[maxn]

,dis[maxn]

;//vis - 點在不在佇列中 cn【x】 - 點x最短路徑上經過的點數 dis - 距離

queue<

int> q;

void

spfa

(int s)

//本題一定有解 所以不用判定有沒正負環

//佇列中加入初始點

dis[s]=0

; vis[s]=1

; q.

push

(s);

while

(q.size()

)}}}

}int

main()

for(

int i=themin;i<=themax;i++

)spfa

(themin)

;printf

("%d"

,dis[themax]);

return0;

}

差分約束 區間選點

給定乙個數軸上的 n 個區間,要求在數軸上選取最少的點使得第 i 個區間 ai,bi 裡至少有 ci 個點 輸入第一行乙個整數 n 表示區間的個數,接下來的 n 行,每一行兩個用空格隔開的整數 a,b 表示區間的左右端點。1 n 50000,0 ai bi 50000 並且 1 ci bi ai 1...

差分約束 解決區間選點問題

給定乙個數軸上的 n 個區間,要求在數軸上選取最少的點使得第 i 個區間 ai,bi 裡至少有 ci 個點。輸入第一行乙個整數 n 表示區間的個數,接下來的 n 行,每一行兩個用空格隔開的整數 a,b 表示區間的左右端點。1 n 50000,0 ai bi 50000 並且 1 ci bi ai 1...

差分約束 區間選點。c

區間選點 給定乙個數軸上的 n 個區間,要求在數軸上選取最少的點使得第 i 個區間 ai,bi 裡至少有 ci 個點,要求使用差分約束 輸入第一行乙個整數 n 表示區間的個數,接下來的 n 行,每一行兩個用空格隔開的整數 a,b 表示區間的左右端點。1 n 50000,0 ai bi 50000 並...