poj 1753

20174/12/8

 太懶了,那幾個比賽補完後就不知道刷什麼題了。算法也不知道學什麼。。

就開個系列吧。-。-跟着前人的腳步走。


PS:

12點多開始擼這第一題。。

第一眼看錯題意  :Each round you flip 3 to 5 pieces 。。還以爲只能翻轉3-5個棋子。。。託託的寫了發暴力。。

神奇的是樣例過了0 0(暴力代碼已經出成題目,請黨和人民放心)

然後.....想到用位來表示狀態,之後!-。-繼續寫暴力。嘎嘎。


用位來表示棋盤的狀態,就 65536種狀態,弄個vis,遍歷過的不在遍歷。然後 1 - 16位挨個翻轉,LOL。

直到找到全黑或者全白,(1表示白0表示黑,全黑0->0000000000000000,全白 65535 -> 1111111111111111)

然後每次按題意翻轉0 0,把該改變的值改掉,0>-1,1->0. 爲了方便得出min的步數,用了bfs來轉移狀態。

#include<stdio.h>
#include<string.h>
#include<queue>
using namespace std;

int vis[70000];
int ct[70000];
char s[5][5];
int flag;

int temp[4][4]={
	1,2,4,8,
	16,32,64,128,
	256,512,1024,2048,
	4096,8192,16384,32768
};

queue<int>q;

int wk(int x,int y,int sum)
{
	sum^=temp[x][y];
	if(x-1>=0)sum^=temp[x-1][y];
	if(y-1>=0)sum^=temp[x][y-1];
	if(x+1<4)sum^=temp[x+1][y];
	if(y+1<4)sum^=temp[x][y+1];
	return sum;
}

void bfs(int x)
{
	if(vis[x])return;
	vis[x]= 1;
	
	for(int i = 0;i < 4; i++)
	for(int j = 0;j < 4; j++)
   {
   	int num = wk(i,j,x);
   	ct[num] = ct[x]+1;
   	if(num==0 || num == 65535)
   	{
	   	printf("%d\n",ct[num]);
	   	flag = 0;
	   	return ;
	   }
	   if(!vis[num])
	     q.push(num);
   }
   return ;
}


int main()
{
	while(~scanf("%s",s[0]))
	{
		flag  =1;
		memset(vis,0,sizeof(vis));
		memset(ct,0,sizeof(ct));
		for(int i =1;i < 4; i++)
		scanf("%s",s[i]);
		
		int sum = 0;
		for(int i = 0;i < 4; i++)
		for(int j = 0;j < 4; j++)
	    {
    		if(s[i][j]=='w')sum+=temp[i][j];	 
    	}

    	if(sum==0||sum==65535)
    	{
	    	printf("0\n");
	    	continue ;
	    }
	    ct[sum] = 0;
	    q.push(sum);
	    while(!q.empty())
	    {
	    	int n = q.front();
    		q.pop();
    		if(flag)
    		{
		    	bfs(n);
		    }
			
    	}
	    
	    if(flag)
	    {
    		printf("Impossible\n");
    	}
	}
	return 0;
}





發佈了123 篇原創文章 · 獲贊 2 · 訪問量 5萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章