題目鏈結
思路:乙個很容易想的dp
設 f i,
jf_
fi,j
表示在前 i
ii 個數中取 j
jj 個所得到的乘積。
則 f i,
j=fi
−1,j
+fi−
1,j−
1×ai
(i
>0,
j>0)
f_=f_+f_×a_i \quad(i>0,j>0)
fi,j=
fi−1
,j+
fi−1
,j−1
×ai
(i>0,
j>0)
邊界: f0,
0=1f
0,i=
0(i≠
0)fi
,0=0
(i≠0
)f_=1\quad f_=0\ (i\ne0) \quad f_=0\ (i\ne 0)
f0,0=
1f0,
i=0
(i̸
=0)f
i,0
=0(i
̸=0
) 但是直接dp會爆空間。。。
觀察到dp時只需呼叫到 fi−
1f_
fi−1
,所以可以用滾動陣列的方式優化空間。
**時間複雜度 o(n
k)
\mathcal o(nk)
o(nk
),空間複雜度 o(n
+k
)\mathcal o(n+k)
o(n+k)
const
mo=1000000007; //膜數
var n,k,i,j:longint;
a:array[0..100010] of longint;
f1,f2:array[0..500] of int64; //安全起見開int64
begin
readln(n,k);
for i:=1 to n do read(a[i]);
f1[0]:=1; //邊界初始化
for i:=1 to n do //dp
begin
for j:=0 to k do
f2[j]:=(f1[j]+f1[j-1]*a[i]) mod mo;
f1:=f2;
end;
writeln(f1[k]);
end.
做完題後仔細想了一下,發現 a
\rm a
a
const mo=1000000007;
var n,k,i,j,a:longint;
f1,f2:array[0..500] of int64;
begin
readln(n,k);
f1[0]:=1;
for i:=1 to n do
begin
read(a); //這樣就可以把a壓成變數了qaq
for j:=0 to k do
f2[j]:=(f1[j]+f1[j-1]*a) mod mo;
f1:=f2;
end;
writeln(f1[k]);
end.
洛谷 P6686 混凝土數學
題目描述 這裡 思路 一 部分分演算法 二 正解 我們考慮對整個序列進行桶排序。我們設每個數出現的次數為 但是,我們會發現這依然過不了 tle了乙個點 我們再次仔細觀察正解的統計方式第一條,發現這可以用字首和優化。於是,這道題就做完了。下面附上 include using namespace std...
洛谷P1142 轟炸 數學
洛谷p1142 轟炸 數學 題意 給出若干個點,求解最多有幾個點在同一直線上 一種做法就是列舉任意兩個點,求他們的斜率然後算一下還有幾個點和他們的斜率一樣,這樣複雜度是 o n 3 n 700 講道理是過不去的,但是資料太水,就過了 另外一種做法就是由樓上提供的,我是來提供 的,列舉以乙個點作為原點...
洛谷 P1372 簡單數學
叮鈴鈴鈴 隨著高考最後一科結考鈴聲的敲響,三年青春時光頓時凝固於此刻。畢業的欣喜怎敵那離別的不捨,憧憬著未來仍毋忘逝去的歌。1000多個日夜的歡笑和淚水,全凝聚在畢業晚會上,相信,這一定是一生最難忘的時刻!為了把畢業晚會辦得更好,老師想要挑出默契程度最大的k個人參與畢業晚會彩排。可是如何挑呢?老師列...