NOIP2016提高組模擬 同餘

2021-07-22 09:00:18 字數 2270 閱讀 6854

我們可以機智地把問題拆分成兩個詢問,以類似字首和的求答案的方法,用1~r的ans減去1~l-1。用一條掃瞄線,把掃過的元素加入乙個桶裡,對於每個詢問,列舉mod p餘q的數,把桶裡的值加入答案。因為當p太小時,這樣的列舉效率很低,所以對於p我們可以分類計算。

1. 當p≤

maxa

[i]−

−−−−

−√時,直接開乙個二維的陣列,表示掃過的元素中mod i 餘 j 的元素個數,詢問時直接用。

2. 當p>

maxa

[i]−

−−−−

−√時,可以證明列舉的數的個數不會超過ma

xa[i

]−−−

−−−√

,所以直接列舉計算。

因為當p<100時用第一種方法不會有影響,所以直接把界限設為100。

var

s:array[0..100,0..100]of longint;

t:array[0..10000] of longint;

a,ans:array[1..100000] of longint;

w:array[0..200005,1..5] of longint;

n,m,x,y,p,q,i,j,z,maxn,sum:longint;

procedure

qsort

(l,r:longint);

var i,j,mid:longint;

begin

i:=l;j:=r;

mid:=w[(l+r)div

2,1];

repeat

while w[i,1]do inc(i);

while mid1] do dec(j);

if i<=j then

begin

w[0]:=w[i];w[i]:=w[j];w[j]:=w[0];

inc(i);dec(j);

end;

until i>j;

if ithen qsort(i,r);

if lthen qsort(l,j);

end;

function

max(x,y:longint):longint;

begin

if x>y then

exit(x) else

exit(y);

end;

begin

readln(n,m);

for i:=1

to n do

read(a[i]);

for i:=1

to m do

begin

readln(x,y,p,q);

inc(sum);

w[sum,1]:=x-1;w[sum,2]:=p;w[sum,3]:=q;w[sum,4]:=i;w[sum,5]:=-1;

inc(sum);

w[sum,1]:=y;w[sum,2]:=p;w[sum,3]:=q;w[sum,4]:=i;w[sum,5]:=1;

end;

qsort(1,sum);

i:=0;

while i<2*m do

begin

inc(i);

while z1] do

begin

inc(z);

inc(t[a[z]]);

maxn:=max(maxn,a[z]);

for j:=1

to100

do inc(s[j,a[z] mod j]);

end;

if w[i,2]<=100

then

begin

ans[w[i,4]]:=ans[w[i,4]]+w[i,5]*s[w[i,2],w[i,3]];

continue;

end;

for j:=0

to max(0,(maxn-w[i,3])div w[i,2]) do

ans[w[i,4]]:=ans[w[i,4]]+w[i,5]*t[j*w[i,2]+w[i,3]];

end;

for i:=1

to m do writeln(ans[i]);

end.

NOIP2016提高組模擬 積木

比賽的時候用了個神奇的小暴力,本來打算拿40分,沒想到暴力出奇蹟,隨機資料下表現優良,居然碾過去了。暴力方法不講,只貼 僅供對拍。正解顯然要用狀態壓縮 看資料範圍 設fs i,0 1 2 s表示當前已選擇的積木集合,i表示在最上方的積木編號,0 1 2表示最上方的積木哪面朝上。轉移方程容易推導。暴力...

計數 NOIP2016提高A組模擬7 15

樣例輸入 2 10 樣例輸出 90資料範圍 剖解題目 題目說的很明了了。思路 求方案數,一般會設計道dp,規律之類的。解法 數字dp,設f i j 表示當前到了第i位,這一位的數字是j的方案數。自然有 f i j f i 1 l f i j 0 l k 且 l 0 and j 0 看到這位數,很明顯...

NOIP2016提高A組模擬9 2 單峰

問1 n,n個數的全排列中有多少個滿足單峰序列的性質,並把答案mod 1e9 7 這題還是很簡單的,一開始打了乙個50分的做法,然後發現答案就是2n 1,然後沒有發現輸入也會爆,於是就得了50分 我們容易發現峰一定是最大的那個數,我們把峰放到每乙個位置上,然後在往峰的左邊隨便填一些數,每種填數的方法...