題意:
hh 有一串由各種漂亮的貝殼組成的項鍊。hh 相信不同的貝殼會帶來好運,所以每次散步完後,他都會隨意取出一段貝殼,思考它們所表達的含義。hh 不斷地收集新的貝殼,因此,他的項鍊變得越來越長。有一天,他突然提出了乙個問題:某一段貝殼中,包含了多少種不同的貝殼?這個問題很難回答……因為項鍊實在是太長了。於是,他只好求助睿智的你,來解決這個問題。
輸入格式
第一行:乙個整數n,表示項鍊的長度。
第二行:n 個整數,表示依次表示項鍊中貝殼的編號(編號為0 到1000000 之間的整數)。
第三行:乙個整數m,表示hh 詢問的個數。
接下來m 行:每行兩個整數,l 和r(1 ≤ l ≤ r ≤ n),表示詢問的區間。
輸出格式
m 行,每行乙個整數,依次表示詢問對應的答案。
分析:
對於若干個詢問的區間[l,r],如果他們的r都相等的話,那麼項鍊**現的同乙個數字,一定是只關心出現在最右邊的那乙個的,例如:
項鍊是:1 3 4 5 1
那麼,對於r=5的所有的詢問來說,第乙個位置上的1完全沒有意義,因為r已經在第五個1的右邊,對於任何查詢的[l,5]區間來說,如果第乙個1被算了,那麼他完全可以用第五個1來替代。
因此,我們可以對所有查詢的區間按照r來排序,然後再來維護乙個樹狀陣列
其實ans【i】表示的是i位之前有多少個不同的數,
#include
#include
using namespace std;
inline
intget_num()
const
int maxn =
5e5+
5, maxc =
1e6+5;
struct question
} q[maxn]
;//定義結構體,用來存放區間的
int n, m, num[maxn]
, last[maxc]
, bit[maxn]
, ans[maxn]
;//num 用來存放原始資料的。ans[用來存放結果的]。
//last[i]-- 用來存放資料i最後一次出現在原陣列的下標。
//bit[i]---用來離散化i分成了幾個部分,表示。
inline
intask
(int x)
inline
void
add(
int x,
int d)
intmain()
ans[q[i]
.id]
=ask
(q[i]
.r)-
ask(q[i]
.l -1)
;}for(
int i =
1; i <= m;
++i)
printf
("%d\n"
, ans[i]);
return0;
}
還有在牛客晚上有乙個和這個題目類似的題目:
在上乙個題目中傳入的是-1,1代表的數量,而這個題目是計算這個區間不同數字的和。所以這裡面傳入的是乙個數num[i],
#include
#include
#include
using namespace std;
const
int n =
5e5+10;
typedef
long
long ll ;
ll c[n]
, ans[n]
, vis[n]
;int a[n]
;int n , m ;
ll lowbit
(int x)
struct node
q[n]
;typedef
long
long ll ;
void
update
(int x ,
int v)
}bool cmp
(node a , node b)
ll ask
(int x)
intmain()
ans[q[i]
.id]
=ask
(q[i]
.r)-
ask(q[i]
.l -1)
;}for(
int i =
1;i <= m ;i ++
)printf
("%lld\n"
,ans[i]);
return0;
}
HH的項鍊(樹狀陣列)區間內不同的數量
hh有一串由各種漂亮的貝殼組成的項鍊。hh相信不同的貝殼會帶來好運,所以每次散步 完後,他都會隨意取出一 段貝殼,思考它們所表達的含義。hh不斷地收集新的貝殼,因此他的項鍊變得越來越長。有一天,他突然提出了一 個問題 某一段貝殼中,包含了多少種不同的貝殼?這個問題很難回答。因為項鍊實在是太長了。於是...
HH的項鍊 樹狀陣列
code 我洛谷部落格 點這裡某一段貝殼中,包含了多少種不同的貝殼?最開始看見這道題時,沒有思路 但再看看,可以非常明了的發現這是乙個樹狀陣列ban題 設有一長為5的項鍊 1 2 3 2 1 然後 m 3 1 52 5 1 3我的思路是這樣,由於要求的是種類數 求l 到 r 的個數 每種貝殼只能存乙...
HH的項鍊(樹狀陣列)
由於詢問的是區間中貝殼的種類數,所以問詢區間中相同種類的貝殼只有乙個會起作用 將i位置的貝殼前一次出現的位置記作pre i 種類為x的貝殼最後一次出現的位置記作f x 類似於鄰接表的nxt和had,利用pre i f x f x i來處理pre 對於每個詢問 l,r 只有pre i 也就是說所處位置...