日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) >

BZOJ 3990: [SDOI2015]排序(搜索+剪枝)

發(fā)布時(shí)間:2025/3/19 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 BZOJ 3990: [SDOI2015]排序(搜索+剪枝) 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? [SDOI2015]排序

Description

小A有一個(gè)1-2^N的排列A[1..2^N],他希望將A數(shù)組從小到大排序,小A可以執(zhí)行的操作有N種,每種操作最多可以執(zhí)行一次,對(duì)于所有的i(1<=i<=N),第i中操作為將序列從左到右劃分為2^{N-i+1}段,每段恰好包括2^{i-1}個(gè)數(shù),然后整體交換其中兩段.小A想知道可以將數(shù)組A從小到大排序的不同的操作序列有多少個(gè),小A認(rèn)為兩個(gè)操作序列不同,當(dāng)且僅當(dāng)操作個(gè)數(shù)不同,或者至少一個(gè)操作不同(種類不同或者操作位置不同).

下面是一個(gè)操作事例:
N=3,A[1..8]=[3,6,1,2,7,8,5,4].
第一次操作,執(zhí)行第3種操作,交換A[1..4]和A[5..8],交換后的A[1..8]為[7,8,5,4,3,6,1,2].
第二次操作,執(zhí)行第1種操作,交換A[3]和A[5],交換后的A[1..8]為[7,8,3,4,5,6,1,2].
第三次操作,執(zhí)行第2中操作,交換A[1..2]和A[7..8],交換后的A[1..8]為[1,2,3,4,5,6,7,8].
Input

第一行,一個(gè)整數(shù)N

第二行,2^N個(gè)整數(shù),A[1..2^N]
Output

一個(gè)整數(shù)表示答案

Sample Input

3

7 8 5 6 1 2 4 3
Sample Output

6

HINT

100%的數(shù)據(jù), 1<=N<=12.

Source

Round 1 感謝ZKY制作非官方數(shù)據(jù)

?

分析:

顯然,對(duì)于每一種方案,我改變其操作順序,仍然不影響結(jié)果,所以我們只需枚舉每種操作做與不做即可,然后將排列數(shù)加入答案即可。

考慮進(jìn)一步優(yōu)化,對(duì)于第i種操作,將序列分為若干個(gè)長(zhǎng)為2^(i-1)的小段,由于每種操作只能用一次,則當(dāng)每個(gè)小段各自元素都連續(xù)且遞增,就不需要這種操作了(相當(dāng)于每2^(i-1)個(gè)為一組,每組都排好了序,要想是整體進(jìn)一步排序,只能依靠下一步操作來排了),如果有一個(gè)不連續(xù)遞增,則將這組分為兩份后交換即可,如果有2組不滿足,分四種情況討論,最后如果超過2個(gè),顯然無法使它們有序,則對(duì)這種方案剪枝。

關(guān)鍵思想是由局部有序一直操作直至全局有序,當(dāng)枚舉第i種操作時(shí),此時(shí)2^(i-2)長(zhǎng)度的段必然是有序的(不合法情況已去除),只需考慮2^(i-1)長(zhǎng)度的段即可。

program sort; vara:array[0..10000]of longint;n,i,m:longint; ans,tot:int64; procedure swap(x1,y1,x2,y2:longint); var i,t:longint; beginfor i:=0 to y1-x1 dobegin t:=a[x1+i]; a[x1+i]:=a[x2+i]; a[x2+i]:=t; end; end; function cheak:boolean; var i:longint; beginfor i:=2 to m do if a[i]<>a[i-1]+1 then exit(false);exit(true); end; procedure dfs(x:longint); var i,j,t,v,s,k:longint; l:int64; w:array[0..2]of longint; beginif x>=n thenbegin if cheak=false then exit;l:=1;for i:=1 to tot do l:=l*i; inc(ans,l); exit; end;t:=1 shl (x+1); v:=1 shl x; s:=v; k:=0;for i:=1 to m div t dobeginif (a[s]+1<>a[s+1])or(a[s] mod v<>0) then begin inc(k); if k>2 then exit;w[k]:=s; end;s:=s+t;end;if k=0 then dfs(x+1);inc(tot);if k=1 then begin swap(w[1]-v+1,w[1],w[1]+1,w[1]+v); dfs(x+1); swap(w[1]-v+1,w[1],w[1]+1,w[1]+v); end;if k=2 thenbeginif (a[w[1]]+1=a[w[2]+1])and(a[w[2]]+1=a[w[1]+1]) thenbeginswap(w[1]-v+1,w[1],w[2]-v+1,w[2]); dfs(x+1); swap(w[1]-v+1,w[1],w[2]-v+1,w[2]);swap(w[1]+1,w[1]+v,w[2]+1,w[2]+v); dfs(x+1); swap(w[1]+1,w[1]+v,w[2]+1,w[2]+v);end;if (a[w[2]]+1=a[w[1]-v+1])and(a[w[2]+v]+1=a[w[1]+1]) thenbegin swap(w[1]-v+1,w[1],w[2]+1,w[2]+v);dfs(x+1); swap(w[1]-v+1,w[1],w[2]+1,w[2]+v);end;if (a[w[1]+v]+1=a[w[2]+1])and(a[w[1]]+1=a[w[2]-v+1]) thenbegin swap(w[1]+1,w[1]+v,w[2]-v+1,w[2]);dfs(x+1); swap(w[1]+1,w[1]+v,w[2]-v+1,w[2]); end;end;dec(tot); end; beginreadln(n);m:=1 shl n;for i:=1 to m do read(a[i]);ans:=0; tot:=0;dfs(0);writeln(ans); end. View Code

?

轉(zhuǎn)載于:https://www.cnblogs.com/qtyytq/p/5903125.html

總結(jié)

以上是生活随笔為你收集整理的BZOJ 3990: [SDOI2015]排序(搜索+剪枝)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。