UVA - 11212 Editing a Book (IDA*)
给你一个长度为n(n<=9)的序列,每次可以将一段连续的子序列剪切到其他地方,问最少多少次操作能将序列变成升序。
本题最大的坑点在于让人很容易想到许多感觉挺正确但实际却不正确的策略来避开一些看似“不好”的操作,比如:不破坏连续的片段,拼接时总是保证多出一个比它左边的数大一的数,等等。而实际上这些策略都是错误的,所以只能暴搜。“将一段连续的子序列剪切到其他地方”等价于“交换两段连续的片段”,因此可以枚举三个划分点i,j,k进行搜索,但这样的话dfs树会很宽大,会TLE。考虑到最少只需要n-1步就能完成任务,因此可以用IDA*来优化,设估价函数h代表当前序列中不正确的数的个数,则每次操作最多将h减少3,用这个来剪枝。
“交换片段”的操作的分界点的选取是个难点,如果自己边界处理的能力不够好的话,不断调参去试也不失为一个好的方法(人体模拟退火)。此外,也可以用C++的库函数copy来简化代码。
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=+;
int a[N],b[N],n,ka;
int calh() {
int ret=;
for(int i=; i<n-; ++i)if(a[i]+!=a[i+])ret++;
if(a[n-]!=n)ret++;
return ret;
} void cut(int l,int m,int r) {
copy(a+m,a+r,b);
copy(a+l,a+m,b+(r-m));
copy(b,b+(r-l),a+l);
} bool dfs(int dep,int mxd) {
int h=calh();
if(h==)return ;
if(*dep+h>*mxd)return ;
for(int i=; i<n; ++i)
for(int k=i+; k<=n; ++k)
for(int j=i+; j<k; ++j) {
cut(i,j,k);
if(dfs(dep+,mxd))return ;
cut(i,i+(k-j),k);
}
return ;
} int IDAStar() {for(int mxd=;; ++mxd)if(dfs(,mxd))return mxd;} int main() {
while(scanf("%d",&n)&&n) {
printf("Case %d: ",++ka);
for(int i=; i<n; ++i)scanf("%d",&a[i]);
printf("%d\n",IDAStar());
}
return ;
}
UVA - 11212 Editing a Book (IDA*)的更多相关文章
- UVa 11212 Editing a Book (IDA* && 状态空间搜索)
题意:你有一篇n(2≤n≤9)个自然段组成的文章,希望将它们排列成1,2,…,n.可以用Ctrl+X(剪切)和Ctrl+V(粘贴)快捷键来完成任务.每次可以剪切一段连续的自然段,粘贴时按照顺序粘贴.注 ...
- UVA 11212 Editing a Book [迭代加深搜索IDA*]
11212 Editing a Book You have n equal-length paragraphs numbered 1 to n. Now you want to arrange the ...
- UVA - 11212 Editing a Book (IDA*搜索)
题目: 给出n(1<n<10)个数字组成的序列,每次操作可以选取一段连续的区间将这个区间之中的数字放到其他任意位置.问最少经过多少次操作可将序列变为1,2,3……n. 思路: 利用IDA* ...
- UVA - 11212 Editing a Book(IDA*算法+状态空间搜索)
题意:通过剪切粘贴操作,将n个自然段组成的文章,排列成1,2,……,n.剪贴板只有一个,问需要完成多少次剪切粘贴操作可以使文章自然段有序排列. 分析: 1.IDA*搜索:maxn是dfs的层数上限,若 ...
- uva 11212 - Editing a Book(迭代加深搜索 IDA*) 迭代加深搜索
迭代加深搜索 自己看的时候第一遍更本就看不懂..是非常水,但智商捉急也是没有办法的事情. 好在有几个同学已经是做过了这道题而且对迭代加深搜索的思路有了一定的了解,所以在某些不理解的地方询问了一下他们的 ...
- UVA 11212 Editing a Book
题意: 有一篇由n个自然段组成的文章.希望将他们排成递增序列.只能剪贴和粘贴交替进行,剪贴时可以剪贴一段连续的自然段. 分析: 用IDA*算法求解.当3*d+h>maxd时剪枝. 代码: #in ...
- Editing a Book UVA - 11212 IDA*
You have n equal-length paragraphs numbered 1 to n . Now you want to arrange them in the order of 1 ...
- 【UVa】11212 Editing a Book(IDA*)
题目 题目 分析 get一下IDA*的技巧,感觉总体来说不难,主要是剪枝比较难想. 这是lrj的代码,比较通俗易懂,关键就是选定一个区间再取出来,插入到一个位置,接下来转移到这个状态. ...
- UVA 11212 IDA*
移动一块连续的区间使得数列递增.问最少次数. 直接IDA*暴搜,只是我没有想到A*函数,所以就随手写了个连续递增块数作为估价函数,WA了,然后除以2,还是WA,除以3,WA,除以4...过了= = # ...
随机推荐
- 前端基础之css样式(选择器)
一.css概述 CSS是Cascading Style Sheets的简称,中文称为层叠样式表,对html标签的渲染和布局 CSS 规则由两个主要的部分构成:选择器,以及一条或多条声明. 例如 二.c ...
- Sublime Text3 打开文档乱码
一.安装包管理器使用Ctrl+~快捷键或者通过View->Show Console菜单打开命令行,粘贴如下代码 import urllib.request,os; pf = 'Package C ...
- php5.6 连接SQL SERVER
PHP Fatal error: Call to undefined function sqlsrv_connect() in php链接sqlserver出现该错误: 原因是:php5.3 及以上版 ...
- [Python]基于CNN的MNIST手写数字识别
目录 一.背景介绍 1.1 卷积神经网络 1.2 深度学习框架 1.3 MNIST 数据集 二.方法和原理 2.1 部署网络模型 (1)权重初始化 (2)卷积和池化 (3)搭建卷积层1 (4)搭建卷积 ...
- Android开发 -- Bootloader
本文转载自:http://blog.csdn.net/jmq_0000/article/details/7378348 LK是什么 LK 是 Little Kernel 它是 appsbl (Appl ...
- Git使用http clone客户端保存用户名密码
使用Git Bash时,用命令git pull或git push时总是要输入密码,很烦躁 解决办法 需要注意的是,这个方法是在Windows下使用 1. 新建环境变量 HOME 值为 %USERP ...
- STL中一些函数的应用
1.nth_element():找到第几大的数.用法:nth_element(a,a+k,a+n),返回一个数组a中第k大的数,时间复杂度比较小,头文件#include <algorithm&g ...
- 进程【TLCL】
ps命令 ps x 加上 "x" 选项(注意没有开头的 "-" 字符),告诉 ps 命令,展示所有进程,不管它们由什么 终端(如果有的话)控制. 在 TTY 一 ...
- POJ 3667 & HDU 3308 & HDU 3397 线段树的区间合并
看到讲课安排上 线段树有一节课"区间合并" 我是迷茫的 因为并没有见过 然后了解了一下题目 发现以前写过 还是很麻烦的树链剖分 大概是 解决带修改的区间查询"连续问题&q ...
- SPOJ375 QTREE - Query on a tree
本文版权归ljh2000和博客园共有,欢迎转载,但须保留此声明,并给出原文链接,谢谢合作. 本文作者:ljh2000 作者博客:http://www.cnblogs.com/ljh2000-jump/ ...