UVALive 4743 (Alice's Cube)DFS

本文介绍了一道关于十六边形上灯的状态转移问题,通过深度优先搜索算法(DFS)来解决如何最少操作次数使特定灯开启或关闭的问题。文章提供了一个完整的C++代码示例,展示了如何实现这一算法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目链接:https://icpcarchive.ecs.baylor.edu/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=2744

题意:

        一个十六边形的啥,然后每个顶点都有一盏灯,每次操作可以开关相连两个顶点的灯,条件是他们的状态必须不同,也就是说一个灯是开着的,另一个灯必须是关着的...问至少经过几次操作可以使1到8这8个顶点都是关着,9-16这8个顶点的灯是开着的...

#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <cmath>
#include <algorithm>
using namespace std;
int k1=0,k2=0,flag,h;
int b[20];
int a[20][5]={{0},{9,2,3,5},{10,4,6,1},{11,4,7,1},{12,3,8,2},{13,6,7,1},{14,5,8,2},{15,5,8,3},{16,6,7,4},
				  {1,10,11,13},{2,9,12,14},{3,9,12,15},{4,10,11,16},{5,9,14,15},{6,13,10,16},{7,11,13,16},{8,12,14,15}};
int DFS(int t)
{
	int i,j;
	if (t>3) return 1;
	if (k1==0 && k2==8)
	{
		flag=1;
		if (h>t) h=t;
		return 1;
	}
	for (i=1;i<=8;i++)
	{
		if (b[i]==1)
		{
			for (j=0;j<4;j++)
			{
				if (b[a[i][j]]==0)
				{
				int k3=k1,k4=k2;
				b[i]=(b[i]+1) % 2;
				b[a[i][j]]=(b[a[i][j]]+1) % 2;
				if (i<=8)
				{
					if (b[i]==1) k1++;
					else k1--;
				}
				else
				{
					if (b[i]==1) k2++;
					else k2--;
				}
				if (a[i][j]<=8)
				{
					if (b[a[i][j]]==1) k1++;
					else k1--;
				}
				else 
				{
					if (b[a[i][j]]==1) k2++;
					else k2--;
				}
				t++;
				DFS(t);
				t--;
				b[i]=(b[i]+1) % 2;
				b[a[i][j]]=(b[a[i][j]]+1) % 2;
				k1=k3;k2=k4;
				}
			}
		}
	}
}
int main()
{
	int T;
	scanf("%d",&T);
	int k=1;
	while (T--)
	{
		int i;
		k1=0;k2=0;
		for (i=1;i<=16;i++)
		{
			scanf("%d",&b[i]);
			if (i<=8) k1+=b[i];
			else k2+=b[i];
		}
		flag=0;
		h=5;
		printf("Case #%d: ",k++);
		DFS(0);
		if (flag==0) printf("more\n");
		else printf("%d\n",h);
	}
	return 0;
}


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值