トピックへのリンク:https://www.luogu.org/problem/P1502
実際には、走査線を見ていません。
私たちは、長方形の長さと幅wとhにすべてのポイントを置くことができます。
左側が右側-wあり、W +です。
セグメントツリーのメンテナンス間隔maxと怠惰なタグ。
そして、走査線の最大を見つけます。
コードは以下の通りであります:
#include <ビット/ STDC ++ H> の#defineは長い長いllの 使用 名前空間STDを、 const int型 MAXN = 20010 ; int型 N、W、H、T、B [MAXN << 1 ]、TOT。 構造体ノード{ LLのMX、タグ。 #define MX(X)ツリー[X] .MX の#defineタグ(x)はツリー[X] .TAG }ツリー[MAXN << 2 ]。 構造体S { int型のx、イル、YH、FL。 S(){} S(int型 XX、INTの YY1、int型 YY2、int型 FF){X = XX;イル= YY1; YH = YY2;フロリダ州=のFF;} } E [MAXN << 1 ]。 インラインブールCMP(SX、SY){ 戻り XX == YX?x.fl> y.fl:XX < YX。 } インラインボイドプッシュダウン(INT P、int型の L、INT R){ 場合(!タグ(P))のリターン; MX(P) + = タグ(P)。 もし(!L = R){ タグ(P << 1)+ = タグ(P)。 タグ(P << 1 | 1)+ = タグ(P)。 } タグ(P) = 0。 } インラインボイド追加(int型 P、int型の L、int型の R、int型のx、int型の Y、int型D){ 場合(X <= L && R <= Y){ タグ(P) + = D。返します。 } INT半ば=(L + R)>> 1 。 場合(X <= MID)を追加(P << 1 、L、中、X、Y、D)。 もし(Y> MID)を追加(P << 1 | 1、中間+ 1 、R、X、Y、D)。 プッシュダウン(P << 1 、L、MID)。 プッシュダウン(P <<1| 1、中間+ 1 、R)。 MX(P) =最大(MX(P << 1)、MX(P << 1 | 1 )); } int型のmain() { scanf関数(" %のD "、&T)。 一方、(t-- ){ memsetの(木、0、はsizeof (木))。 TOT = 0 ; scanf関数(" %D%D%D "、&N、&W&H)。 以下のために(int型 i = 1 ; iが++; iが<= N ){ INTのX、Y、V。 scanf関数(" %D%D%D "、およびX&Y、およびV)。 E [ ++ TOT] .X = xは、B [TOTは] = yと、 E [TOT] .yl = Y; E [TOT = Y + H .yh 1 ; E [TOT]の.Fl = V。 E [ ++ TOT] .X = X + W- 1 ; B [TOTは】= Y + H- 1 。 E [TOT] .yl = Y; E [TOT = Y + H .yh 1 ; E [TOT]の.Fl = - V。 } ソート(B + 1、B + 1 + 2 * N)。 TOT =一意(B + 1、B + 1 + 2 * n)で-B- 1 。 ソート(E + 1、E + 1 + 2 *のN、CMP)。 LL ANS = 0 。 以下のために(int型 i = 1 ; iは= < 2 * N; I ++ ){ int型の H1 = LOWER_BOUND(B + 1、B + 1回の + TOT、E [i]は.yh) - B。 int型 H2 = LOWER_BOUND(B + 1、B + 1回の + TOT、E [I] .yl) - B。 E [i]は.yl = H2; E [i]を.yh = H1。 } のために(intです i = 1 ; iが= < 2 iは++; * N ){ 追加(1、1、2 *のN、E [i]は.yl、E [i]は.yh、E [I]の.Fl)を、 ANS = MAX(ANS、MX(1 ))。 } のprintf(" %LLDする\ n " 、ANS)。 } 戻り 0 。 }