AT274の技術だったりなかったり

あっとのTECH LOG

競プロのこととか技術のこととか。たまに日常を書きます。

JOI難易度6 ピザ

問題原文

https://www.ioi-jp.org/joi/2008/2009-ho-prob_and_sol/2009-ho.pdf#page=4

問題要旨

長さ  D の円環上に  N 個の店舗がある。(入力で与えられるのは N- 1 個で、店舗0は座標0にある) また注文が  M 個きており、円環状の宅配場所が与えられる。
各注文について最も近い店舗から宅配するとき、全注文を処理する場合の総宅配距離はいくらになるか?

  •   1 \leq D \leq 10^{9}
  •   1 \leq N \leq 10^{5}
  •   1 \leq M \leq 10^{4}

解法

各注文について最も近い店舗を二分探索で求めればよい。
D=8、宅配場所=7, 店舗1= 5 のような時は、そのまま進んで店舗0に届ける方が近くなるように処理する必要があるが、店舗 N + 1 =  D となるようなものを追加しておけば問題なく処理できる。

実装

Pythonだと A[-1] みたいなことがなまじできてしまってREでなくWAを吐くケースがあるので注意すること。
S[i - 1] が S[-1] になるケースですね。

from bisect import bisect_left
D = int(input())
N = int(input())
M = int(input())
S = [0] + sorted([int(input()) for _ in range(N - 1)]) + [D]
K = [int(input()) for _ in range(M)]


ans = 0
for k in K:
    i = bisect_left(S, k)
    ans += max(0, min(S[i] - k, k - S[i - 1]))

print(ans)

感想

Pythonのスライスは便利だけどこういう時は十分注意する。