[テンプレート] [] [ツリー]データ構造会長ツリー

スキルI:離散重複排除機能

int型私は= 1 scanfの(; I <= N-Iが++)" %のD "、&​​A [I])を、B [I] = A [I]; 
    (Bソート + 1、B + N-+ 1 );
     INT UNIQUE = nnの(B + 1、B + N-+ 1)-B- 1。 ; // Xの数は、その後、ポインタはNN、最初の番号の位置にNN X + 1を停止し、それ以降の繰り返し要素であると仮定するためINT I = 1 ; I <= N; I ++の
        ID [I] = LOWER_BOUND(Bの+ 1、B + NN + 1、[I]) - B;新しい離散値の後//

スキルII:できる永続的なデータ構造

患部を変更し、新しいポイントを記録する新しい点へのポインタは、容易に検索することができます

ボイドアップデータ(int型 L、INT R、INT&NW、INTプリ、INT X)
{ 
    NW = ++ CNT。
    T [NW] [事前] =さt; tは[NW] .SUM ++ もし(L == R)のリターン;
    INT半ば=(L + R)>> 1 もし(MID> = X)アップデータ(L、中、T [NW]を得た。LC、T [事前]を得た。LC、X)。
    他のアップデータ(MID + 1 、R、T [NW] .RC、T [事前] .RC、X)。
}

スキルIII:船舶の範囲は[R] -a [L-1]に分解することができます

各ブランチNを持っているにもかかわらず

INTクエリ(INT L、INT R、INT LL、INT RR、INT KK)
{ 
    場合(L == R)戻りL。
    INT S = T [T [RR]を得た。LC] .SUM - T [T [LL]を得た。LC] .SUM。
    INT半ば=(L + R)>> 1 場合(S> = KK)戻りクエリ(L、中、T [LL]を得た。LC、T [RR]を得た。LC、KK)。
     戻りクエリ(MID + 1、R、T [LL] .RC、T [RR] .RC、kk- S)。
}

最後に:会長ツリーテンプレート

// luogu P3834 
の#include <cstdioを> 
する#include <cstdlib> 
書式#include <アルゴリズム>
 使用して 名前空間はstdを、
INTのN、M。
const  int型 N = 200003 ;
INT [N]、B [N]、ID [N]。

構造体ノード
{ 
    int型の和、LC、RC。
} T [N * 40 ]。
int型のCNT、RT [N]。
INTのビルド(int型 L、INT R)
{ 
    int型 RT = ++ CNT。
    T [RT] .SUM = 0 もしリットル(!=R)
    { 
        int型ミッド=(L + R)>> 1 
        T [RT]を得た。LC = ビルド(L、MID)。
        T [RT] .RC =ビルド(MID + 1 、R)。
    } 
    戻りRT; 
} 
ボイドアップデータ(int型 L、INT R、INT&NW、INTプリ、INT X)
{ 
    NW = ++ CNT。
    T [NW] [事前] =さt; tは[NW] .SUM ++ もし(L == R)のリターン;
    INT半ば=(L + R)>> 1 もし(中期> =X)アップデータ(L、中、T [NW]を得た。LC、T [事前]を得た。LC、X)。
    他のアップデータ(MID + 1 、R、T [NW] .RC、T [事前] .RC、X)。
} 

INTクエリ(INT L、INT R、INT LL、INT RR、INT KK)
{ 
    場合(L == R)戻りL。
    INT S = T [T [RR]を得た。LC] .SUM - T [T [LL]を得た。LC] .SUM。
    INT半ば=(L + R)>> 1 場合(S> = KK)戻りクエリ(L、中、T [LL]を得た。LC、T [RR]を得た。LC、KK)。
     戻りクエリ(MID + 1、R、T [LL] .RC、T [RR] .RC、kk-  S)。
}

INT メイン()
{ 
    scanfの(" %のDの%のD "、およびN-、&M)
     のためのINT I = 1 ; I <= N; I ++)scanfの(" %Dを"、&​​A [I])、B [I ] = A [I]、
    ソート(Bの + 1、B + N-+ 1 );
     int型 NN = UNIQUE(Bの+ 1、B + N-+ 1)-B- 1。 ; // Xの数は、その後、ポインタがNNを停止することを前提と番号x + 1の第1の位置における 
     // 離散重量に対する 
    RTを[ 0 ] =(ビルド1 、NN)を、
     ためINT I =。1 ; I <= N; I ++ 
    { 
        ID [I] = LOWER_BOUND(Bの+ 1、B + NN + 1、A [I]) - B; 
        アップデータ(1、NN、RT [I]、RT [I- 1 ] 、ID [I]); //は、離散的な数にアレイを取る 
    } // 離散した後に新しい値
    int型、X、Y Kを、
     一方(M-- 
    { 
        scanfの(" %D%D%D "、&​​X&Y、およびK); 
        のprintf(" %d個の\ N- "、[クエリ(B 1、NN、RT [X- 1 ]、RT [Y]、K)]); // シリアル番号B配列にディスクリート
    }
     戻り 0 
}

おすすめ

転載: www.cnblogs.com/xwww666666/p/11270249.html