在乙個數軸上,有些人要從某個點到達另乙個點。
計程車從最左端出發,將所有人送到它們的目的地,最終到達最右邊的點。
計程車只能做乙個乘客,並且可以在圖中將乘客丟下。
問最短時間。
一看就覺得是神仙題,
往dp方向思考,沒有一點點長進……
壓根就沒有想過貪心……
然而這題又沒得打暴力,於是一分都沒有拿。
面對這種神仙題,為什麼我沒有想到貪心……
首先將有用功加入答案中。
計程車走過的路徑一定連在一起的,如果我們新增一條從m
mm到0
00的路徑,就能保證它最終能到達m
mm點。這樣路徑就構成了乙個環。
可以通過各個點將數軸分成很多段,每一段上有一些往左走的路,有一些往右走的路。
大多時候這些向左走和向右走的路徑條數是不一樣的,但我們求的是環(尤拉迴路)。
於是我們相減,取絕對值,強制新增路徑。
這樣搞出來之後可能不會連通,但由於有條從m
mm到0
00的路徑,如果不連通,一定可以有種花費同樣代價的方式使得它們串成乙個尤拉迴路。所以直接新增就好。
那麼我們差分處理一下就搞定了。
然後還有一種神奇的方法。
同樣要加上m
mm到0
00的路徑。
首先將有用功加入答案中,然後的具體做法比較神奇:將起點和終點分別排序,下標相同的座標相減取絕對值,加入答案中。
然後就沒了。
這是什麼神仙做法?
根據我的理解,這也是搞出尤拉迴路,然後貪心地將起點和終點配對,即連在一起。
配對的時候排序,然後兩兩配,這樣是最小的。我自己想了乙個不完整的證明:假設有a1≤
a2a_1\leq a_2
a1≤a2
和b1≤b
2b_1\leq b_2
b1≤b2
,可以證明∣a1
−b1∣
+∣a2
−b2∣
≤∣a1
−b2∣
+∣a2
−b1∣
|a_1-b_1|+|a_2-b_2|\leq |a_1-b_2|+|a_2-b_1|
∣a1−b
1∣+
∣a2
−b2
∣≤∣a
1−b
2∣+
∣a2
−b1
∣。在數軸上分類討論就可以證明了。
仔細想想,我發現這似乎已經無視了可以把乘客中途扔下車的操作(除了將幾個尤拉迴路連在一塊之外)!
路徑分成了很多段,如果拆開來這樣做,就相當於可以中途將乘客趕下車,這樣一定是沒有問題的。這幾段中,中間的每個交點既是起點,又是終點,它們自己和自己配對,不會優於與真正的起點終點配對。
這個東西感性理解一下吧……不會證明。
using
namespace std;
#include
#include
#include
#define n 100010
int n,end;
struct op o[n*2]
;int m;
inline
bool
cmp(
const op &a,
const op &b)
long
long ans;
intmain()
; o[
++m]=;
for(
int i=
1;i<=n;
++i)
; o[
++m]=;
}sort
(o+1
,o+m+
1,cmp)
;for
(int i=
2,j=o[1]
.ty;i<=m;
++i)
printf
("%lld\n"
,ans)
;return0;
}
差分陣列 JZOJ 3187 的士
description bessie為農場上的其他奶牛提供的士服務。奶牛們在一條長為m 1 m 1,000,000,000 的柵欄的不同位置上。不幸的是,它們厭倦了它們現在所在的位置而想要去柵欄上其他的位置。bessie必須把她每乙個朋友從它們各自的起始地接上車然後送它們到目的地。但bessie的車...
JZOJ5242 GDOI模擬 矩陣
給出乙個n m 的01 矩陣,求其中有多少個連續子矩陣,使得其面積大於等於k,且其中不包含1。非常經典的一道題目。首先我們很容易知道n 3的方法。那麼我們來優化一下。我們先求出f i j 表示從 i,j 向右連續1的數量。然後把這些從大到小的插入 桶排一下 然後如果上面或下面已經有了就合併,然後算出...
JZOJ5242 GDOI2018模擬8 8 矩陣
description 給出乙個n m 的01 矩陣,求其中有多少個連續子矩陣,使得其面積大於等於k,且其中不包含1。input 第一行為用空格隔開的三個整數n,m,k。分別表示矩陣的行數,列數和子矩陣的最小面積。接下來的n 行每行為用空格隔開的m 個整數,為題目中給出的矩陣。output 輸出一行...