山门 dfs

卡尔接到任务去打败一个恶魔,恶魔藏于受魔法保护的山门后。他的师傅告诉他,山门前的石头必须按回文序列分割,每段至少包含k个石头。给定石头序列和k值,卡尔需判断是否能按要求分割。程序通过查找并DFS验证所有可能的回文子序列来解决此问题。
摘要由CSDN通过智能技术生成

1553年,卡尔已经成为一个能力强大的强者,被委派去打倒一个隐藏得极深的恶魔。据说这个恶魔从地狱而来,所到之处都是尸骸,行踪诡异,经常消失。几天前,卡尔的师傅米勒尔试图讨伐这个恶魔,但险些丧命。他叮嘱卡尔要小心,然后告诉了卡尔恶魔所在的地点。卡尔立即动身前往,来到了恶魔所在的山门。虽然被称为山门,但却因恶魔施下的魔法而无法直接看到。据米勒尔所说,山门前有n个石头,水平地摆放在地上。这些石头最多只有10种形状,米勒尔将这些形状标记为0到9的数字,并在画册上标出每种形状的石头对应的数字。卡尔需要在某些石头之间放置隔离符,使得这些石头被分隔成若干部分,之后催动咒语。只有分隔出的每个部分的石头形状都是回文的、且每个部分的石头个数至少为k,才能破解山门的法术。

请协助卡尔判断是否存在一种分隔方式,使得法术得以被破解。

输入描述

先给出一个整数串(长度为n),再给出一个整数k,表示每个部分要求回文的最小石头个数。

范围:

2≤k≤n≤16

输出描述

如果存在,那么输出Yes,否则输出No

样例1

输入

0022 2

输出

Yes

样例2

输入

012210 2

输出

Yes

样例3

输入

0101 2

输出

No

思路:

先把所有大于k的回文找出来,存在数组中 比如a[1][3]==1就是从s[1]到s[3]是回文,然后跑一遍dfs

看能不能到达最后一个 即s.length()

#include<iostream>
#include<algorithm>
#include<cstring>
#include<string>//to_string(value)
#include<cstdio>
#include<cmath>
#include<vector>//res.erase(unique(res.begin(), res.end()), res.end())
#include<queue>
#include<stack>
#include<map>
#include<set>//iterator,insert(),erase(),lower/upper_bound(value)/find()return end()
#define ll long long
using namespace std;
string s;
int a[50][50];
bool dfs(int be,int mo){
	if(be-1==mo) return true;
	for(int i=0;i<s.length();i++){
		if(a[be][i]==1){
			if(dfs(i+1,mo)) return true;
		}
	}
	return false;
}
signed main()
{
	cin>>s;
	int k;
	cin>>k;
	for(int i=0;i<s.length();i++){
		for(int j=i+k-1;j<s.length();j++){
			int l=i,r=j;
			int pan=1;
			while(l<=r){
				if(s[l]!=s[r]){
					pan=0;
					break;
				}
				l++,r--;
			}
			if(pan==0) continue;
			else{
				a[i][j]=1;
			}
		}
	}
	if(dfs(0,s.length()-1)) cout<<"Yes";
	else cout<<"No";
 } 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值