ハング電気マルチ補正第2フィールド1012 L - 最長サブアレイCEセグメントツリー

この問題は、本当にショーです。私がしなければなりませんでした。書くことができるものの良い感じでセグメントツリー。

トピックの効果は:各番号について、またはKの発生よりも、この子が持っていたノーショーの文字列、またはそれ以上:あなたの文字列を与えるために、サブストリングが最も長いが長い、以下の条件を満たすように尋ねました。

私たちは、私は、確かに遠いが、条件を満たすために、左見つけることを願っていますそれぞれの場所には、最大ではなく、宮を維持尊重しますか?

だから、どのように我々は、最も遠いが条件を満たして見つけるのですか?それでは、私たちはいくつかのものを維持する必要がありますか?

我々は、[] T配列を維持し、T [J] = M iは位置jから左へのビットを表し、条件満足する数メンテナンスセグメントツリー、(いずれか0として、kは1以上です)。

私は、我々が現在の位置にC-1を追加する必要がある各位置、現在の代表点、区間0の長さ

場合右点、他の数は、Xの左の点を除いて、私はのように[I、i]は、この範囲の位置とすることができるように、我々はTを議論するたびに[i]は、[I] = xとして、Iの位置でありますxは、他の人が0回登場している、一度だけ以内に現れ0は確かに可能である現れ、第1プラスC-1(-1位置ので、私はさらに、生存可能な左点Xとして議論する必要がある場合)

その後、我々は数によるi番目の場所に[i]は私の位置は、位置および位置の値に等しく[i]を、可能にするために使用間隔に[i]は、次いで得られた現在位置が登場検討しますしかし、今になっていません。私たちは、必要とします

一つの位置から-1の完全な値、[i]は、間隔が利用可能でなくなったの代表です。そして、私たちの前方にkの現在の位置から[i]のK-1 [i]の位置より前の位置で、前回の位置は使用できませんが、右側の[i]は、新規に追加されますので、このセクションでは利用できないが利用可能になるであろう、それは元の値を表す、+1の範囲内であるべきであるが、利用できない現在利用可能です。

#include <ビット/ STDC ++ H>
 に#define LL長い長
 の#define LSONのRT << 1つ
 の#define rsonのRT << 1 | 1
 使用して 名前空間STDを、
const  int型 MAXX = 1E5 + 6 構造体ノード{
    int型のL、R。
   int型、CNTを過ごします。
}ツリー[MAXX << 2 ]。
INT [MAXX]。
INT 前[MAXX]。
int型N、C、K。
ベクター < INT > G [MAXX]。
ボイド push_down(INT RT){
    場合(ツリー[RT] .laze){
      ツリー[LSON] .CNT + =ツリー[RT] .laze。
      ツリー[rson] .CNT + = ツリー[RT] .laze。
      ツリー[LSON] .laze + = ツリー[RT] .laze。
      ツリー[rson] .laze + = ツリー[RT] .laze。
      ツリー[RT] .laze = 0 
   } 
} 
ボイド buildtree(INT RT、INT L、INT R){ 
    ツリー[RT] .L = L。
    ツリー[RT] .R = R。
    ツリー[RT] .laze = 0 
    ツリー[RT] .CNT = 0 もし(L == R){
        リターン
    } 
    INT半ば=(L + R)>> 1 
    buildtree(LSON、L、MID)。
    buildtree(rson、ミッド + 1 、R)。
} 
ボイド更新(INT RT、INT UL、int型 UR、INT W){
     int型 L = ツリー[RT] .L。
    INT R = ツリー[RT] .R。
    もし(UL <= 1 && R <= UR){ 
        ツリー[RT] .CNT + = W。
        ツリー[RT] .laze + = W。
        返します
    } 
    push_down(RT)。
    INT半ば=(L + R)>> 1もし(UR <= MID){ 
        更新(LSON、UL、UR、W)。
    } そう であれば(UL> MID){ 
        更新(rson、UL、UR、W)。
    } { 
        更新(LSON、UL、中、W)。
        アップデート(rson、ミッド + 1 、UR、W)。
    } 
    ツリー[RT] .CNT = MAX(ツリー[LSON] .CNT、ツリー[rson] .CNT)。
} 
INTクエリ(INT RT){
     int型 L = ツリー[RT] .L。
    INT R = ツリー[RT] .R。
    もし(1- ==のR){
        戻りL。
    } 
    push_down(RT); 
    INT半ば=(L + R)>> 1 もし(ツリー[LSON] .CNT == C){
         戻りクエリ(LSON)。
    } そう であれば(ツリー[rson] .CNT == C){
         戻りクエリ(rson)。
    } {
         リターン - 1 
    } 
} 
int型のmain(){
   しながら(〜のscanf(" %D%D%D "、&​​N、&C&K)){
       ためint型 i = 1 ; iが= Cを<; iは++ ){
        G [i]が.clear(); 
        G [i]が.push_back(0 )。
      } 
      のmemset(前、0はsizeof (PRE))。
      以下のためにint型 i = 1 ; iが<= N; iが++ ){ 
        scanf関数(" %dを"[I])。
        G [I]一back(I)。
      } 
      buildtree(11 、N)
      もし(Kの== 1 ){ 
        のprintf(" %d個の\ n " 、N)。
        続け; 
      } 
      INT ANS = 0 以下のためにint型 i = 1 ; iが<= N; iは++ ){
          int型のx = [I]。
         int型のp = ++ プリ[[I]]; 
         アップデート(1、I、I、C- 1 )。
         もし(G [I] [P- 1 ] + 1 <= G [I]、[P] - 1 
            アップデート(1、G [I] [P- 1 ] + 1、 G [I]、[P] - 1 - 1 )。
         もし(P> = k)を
            更新(1、G [I] [PK] + 1、G [I] [P-K + 1 ]、1 )。
         INT POS =クエリ(1 )。
         もし(POS =! - 1 ){ 
            ANS = MAX(ANS、I-POS + 1 )。
         } 
      } 
      のprintf(" %d個の\ n " 、ANS)。
  } 
  戻り 0 
}

 

おすすめ

転載: www.cnblogs.com/bluefly-hrbust/p/11420399.html