HDU 4021 24 Puzzle(11年上海 15數位)

來源:互聯網
上載者:User

轉載請註明出處,謝謝http://blog.csdn.net/acm_cxlove/article/details/7854526      
by---cxlove

題目:給出24個格子的數位的初始態和目標態,然後問能不能轉換

http://acm.hdu.edu.cn/showproblem.php?pid=4021 

思路:看起來很像著名的“八數位”問題,首先,針對八個特殊位置(死角),如果這裡有空位就把它和相鄰的位置交換,這樣之後如果兩個狀態的對應死角上的數字不同,那麼顯然是不能達到指定狀態的,因為無法把死角處的數字換出去。

搞定了死角後就只剩下4×4的board了,這就變成了八數位問題的拓展——15數位。首先想想八數位是如何判斷有解的:首先把所有數字(不包括空位的0)寫成一行,就得到了一個1~8的排列,考慮空位的交換情況:1.左右交換,2.上下交換。對於左右交換而言,是不會改變寫出的排列的逆序數的;而對上下交換,相當於在排列中向前或向後跳了兩個位置,那麼要麼兩個數都比它大或小,這樣逆序數加2或減2,要麼兩個數一個比它大一個比它小,這樣逆序數不變,綜上,對於八數位問題,操作不會改變逆序數的奇偶性,所以只有初始狀態和指定狀態的逆序數奇偶性相同就有解。

弄清楚了八數位,擴充起來就容易了,現在我們將其擴充到N維(即N*N的board,N*N-1數位問題)。

首先無論N的奇偶,左右交換不改變逆序數,N為奇數時:上下交換逆序數增加N-1或減少N-1或不變,因為N為奇數,所以逆序數奇偶性不變;而N為偶數時:上下交換一次奇偶性改變一次。

結論:N為奇數時,初始狀態與指定狀態逆序數奇偶性相同即有解;N為偶數時,先計算出從初始狀態到指定狀態,空位要移動的行數m,如果初始狀態的逆序數加上m與指定狀態的逆序數奇偶性相同,則有解。

好了,現在這道題就簡單了,計算逆序數和空格要移動的行數即可。

#include<iostream>#include<cstdio>#include<map>#include<cstring>#include<cmath>#include<vector>#include<queue>#include<algorithm>#include<set>#define inf 110000000#define M 10005#define N 10005#define Min(a,b) ((a)<(b)?(a):(b))#define Max(a,b) ((a)>(b)?(a):(b))#define pb(a) push_back(a)#define mem(a,b) memset(a,b,sizeof(a))#define LL long long#define MOD 1000000007using namespace std;int init[24],goal[24];int a[8]={0,1,2,7,16,21,22,23};int b[16]={3,4,5,6,8,9,10,11,12,13,14,15,17,18,19,20};int gao(int b){    if(b==0||b==2) return 3;    if(b==1||b==7) return 6;    if(b==16||b==22) return 17;    else return 20;}int main(){    int t;    scanf("%d",&t);    while(t--){        for(int i=0;i<24;i++)            scanf("%d",&init[i]);        for(int i=0;i<8;i++)            if(init[a[i]]==0)                swap(init[a[i]],init[gao(a[i])]);        for(int i=0;i<24;i++)            scanf("%d",&goal[i]);        for(int i=0;i<8;i++)            if(goal[a[i]]==0)                swap(goal[a[i]],goal[gao(a[i])]);        bool ans=true;        for(int i=0;i<8&&ans;i++){        //    cout<<init[a[i]]<<" "<<goal[a[i]]<<endl;            if(init[a[i]]!=goal[a[i]])                ans=false;        }        if(!ans){puts("Y");continue;}        int cnt1=0,cnt2=0,pos1=0,pos2=0;        for(int i=1;i<16;i++){            if(init[b[i]]==0){pos1=i;continue;}            for(int j=0;j<i;j++)                if(init[b[j]]>init[b[i]])                   cnt1++;        }        for(int i=1;i<16;i++){            if(goal[b[i]]==0){pos2=i;continue;}            for(int j=0;j<i;j++)                if(goal[b[j]]>goal[b[i]])                   cnt2++;        }        if((abs(pos1/4-pos2/4)+cnt1-cnt2)%2==0) puts("N");        else puts("Y");    }    return 0;}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.