2019 09 07 NOIP提高組 模擬 A 組

2021-09-26 23:59:33 字數 1792 閱讀 4177

t1:這題較為簡單。

只需求出去掉每乙個位置之後逆序對個數減少多少個,然後推一下式子就好了。

t2:這題比較靈活。

我們把所有的字串放在乙個矩陣上,然後從左往右考慮每一列,我們發現其實所有字串就是在不斷地分組。把每一列中字母相同的字串分到同一組,然後在看下一列。最終m列之後每乙個字串都別分到了不同的組,這樣就是合法的。

那麼我們就可以dp了。設f[i][l][r][c]表示現在處理到第i列,l~r行最大的字元填c的且當前l~r行的字典序有嚴格保證的方案數。(注意我們是從m往1處理的)。

在轉移時,我們列舉乙個r1和d,表示第i列r+1~r1行填d,接著我們就f[i][l][r1][d]+=f[i][l][r][c]*f[i+1][r+1][r1][e]。由於e的任意性,我們可以邊求f邊求和,那麼轉移時我們就不用列舉e了。

這樣的複雜度時能過的。但是還有一些細節要注意,比如說我們要判斷r+1~r1填d是否合法,還有就是在l~r都能填c的情況下,我們要把g[i+1][l][r]作為f[i][l][r][c]的初值(g就是f的和)。

細節較多,貼一下**:

#include#include#include#define ll long long

#define maxn 60

#define maxm 30

#define maxv 30

#define mod 990804011

ll a[maxn][maxm],f[maxm][maxn][maxn][maxv],g[maxm][maxn][maxn],n,m,ans;

char a1[maxn][maxm];

int main()

else a[i][j]=-1;

for(l=1;l<=n;l++)

if(a[l][m]!=-1)f[m][l][l][a[l][m]]=1;

else

for(c=1;c<=26;c++)f[m][l][l][c]=1;

for(c=0;c<=26;c++)

for(l=1;l<=n;l++)

for(r=l;r<=n;r++)

for(i=m-1;i>=1;i--)

for(c=0;c<=26;c++)

for(l=1;l<=n;l++)

g[i][l][r]=(g[i][l][r]+f[i][l][r][c])%mod;

}}printf("%lld",g[1][1][n]);

}

t3:這是一道偏數學的題目。

首先我們把所有x[i]減1,然後發現f就等於從(0,0...,0)走到(x[1],x[2],...,x[k])的方案數%2。

然後我們就可以開始推式子:

首先對於二維情況:f=c(x1+x2,x2)。

那麼擴充套件到k維的情況就是:

現在就是要求f的奇偶性。首先很容易得出n!中2因子的個數=

這時又到感性理解的時候了:如果存在某個x[i]和x[j]相加時在二進位制狀態下發生了進製,那麼f一定含有2因子,即f的貢獻為0。

這其實不難理解。那麼現在我們可以得出結論,如果想要f對答案有貢獻,那麼所有x的二進位制位上最多只能有乙個1(即不能進製)。

那麼就可以數字+狀壓dp了。設f[i][s]表示當前到第i位,其中s狀態下的x前面已經頂到了上限(就是數字dp的常見套路)的方案數。列舉所有x的第i-1位填什麼,即乙個新的01集合s1,判斷是否合法後轉移即可。

最後要優化一下才能過。

NOIP提高組 矩陣

在麥克雷的面前出現了乙個有n m個格仔的矩陣,每個格仔用 或 表示,表示這個格仔可以放東西,則表示這個格仔不能放東西。現在他拿著一條1 2大小的木棒,好奇的他想知道對於一些子矩陣,有多少種放木棒的方案。因為棍子是1 2的,所以很容易就能發現,兩個被分割的塊,除了跨越兩個塊擺放木棍的方案數會對答案有影...

NOIP提高組2005 過河

過河 river 問題描述 在河上有一座獨木橋,乙隻青蛙想沿著獨木橋從河的一側跳到另一側。在橋上有一些石子,青蛙很討厭踩在這些石子上。由於橋的長度和青蛙一次跳過的距離都是正整數,我們可以把獨木橋上青蛙可能到達的點看成數軸上的一串整點 0,1,l 其中l是橋的長度 座標為0的點表示橋的起點,座標為l的...

NOIP提高組 20151029模擬

其實這套題目並不算太難,但是還是發揮不了100 水平。第一題直接線性篩法,求出質數,然後就可以判斷乙個數是否為質數了。這道題還可以用miller rabin去求,後者的速度較快,如果資料再大些,就要使用後者了。第二題,比賽時發現了,當n 7時,答案會每四個一迴圈,但是就沒有繼續往下想,其實想下去會想...