【NOIP2016】組合數問題
阿新 • • 發佈:2018-11-10
本題在洛谷上的連結:https://www.luogu.org/problemnew/show/P2822
就在十一假期某學堂裡有幸聽出題人zhx大神講課。。。
都說是水題,但還是需要技巧滴。首先得知道組合數的那個在楊輝三角里體現得淋漓盡致的性質:c[n][m]=c[n-1][m-1]+c[n-1][m]。
考慮到多組資料,但k是一定的,可以再開個陣列來存到(i,j)時在第i行前j個的答案數,然後對應查詢累加即可。
本以為這樣就能過的,可是隻有55分?輸出中間結果一看,溢位了。。。
優化一下,判斷是否能被k整除時,直接c[i][j]%=k就好,若是0則令答案數加1。
1 #include <cstdio> 2 #include <algorithm> 3 4 using namespace std; 5 6 const int mmax = 2005, maxt = 1e4 + 5; 7 8 int in[maxt], im[maxt], tri[mmax][mmax], ans[mmax][mmax]; 9 10 int main() { 11 int t, k, maxn = 0; 12 scanf("%d%d", &t, &k); 13 forAC程式碼(int i = 1; i <= t; ++i) { 14 scanf("%d%d", &in[i], &im[i]); 15 maxn = max(maxn, in[i]); 16 } 17 for (int i = 0; i <= maxn; ++i) 18 for (int j = 0; j <= i; ++j) { 19 if (!j || j == i) { 20 tri[i][j] = 1; 21 if(j == i) ans[i][j] = ans[i][j - 1]; 22 } 23 else { 24 tri[i][j] = (tri[i - 1][j - 1] + tri[i - 1][j]) % k; 25 if (!tri[i][j]) ans[i][j] = ans[i][j - 1] + 1; 26 else ans[i][j] = ans[i][j - 1]; 27 } 28 } 29 for (int i = 1; i <= t; ++i) { 30 int out = 0; 31 for (int j = 0; j <= in[i]; ++j) 32 if (j <= im[i]) out += ans[j][j]; 33 else out += ans[j][im[i]]; 34 printf("%d\n", out); 35 } 36 return 0; 37 }