[2016-02-27][UVA][11212][Editing a Book]

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[2016-02-27][UVA][11212][Editing a Book]相关的知识,希望对你有一定的参考价值。

[2016-02-27][UVA][11212][Editing a Book]


  • 时间:2016-02-26 19:38:44 星期五
  • 题目编号:UVA 11212
  • 题目大意:给定长度为n(值为1~n)的序列,求把该序列 复制/粘贴 成1~n 的排列最少步数
  • 分析:
    • 状态空间搜索,但是每次状态转移的方式有多种,可能会T,
    • 发现,最多 操作 的次数:n~1的序列,每次操作 长度为1的连续段,那么需要 n-1 次操作
    • 可以用IDA*算法
    • 剪枝,每次操作之后,每个数字的后继数字不正确的数目h,最多减少3,
    • 那么至少需要 h / 3 次操作才能,达到目标
  • 方法:IDA*
    • 数据是10个长度,所以,结贴操作直接for语句完成      
    • dfs过程,层数达到maxd,判断是否排列好
    • 如果预测最少层数大于maxd,直接返回
    • dfs ,枚举起点和宽度,截取这一段数字,放在起点前面任意一个点,然后进入下层dfs


#include <vector>
#include <list>
#include <map>
#include <set>
#include <deque>
#include <queue>
#include <stack>
#include <bitset>
#include <algorithm>
#include <functional>
#include <numeric>
#include <utility>
#include <sstream>
#include <iostream>
#include <iomanip>
#include <cstdio>
#include <cmath>
#include <cstdlib>
#include <cctype>
#include <string>
#include <cstring>
#include <cstdio>
#include <cmath>
#include <cstdlib>
#include <ctime>
using namespace std;
typedef long long LL;
#define CLR(x,y) memset((x),(y),sizeof((x)))
#define FOR(x,y,z) for(int (x)=(y);(x)<(z);++(x))
#define FORD(x,y,z) for(int (x)=(y);(x)>=(z);--(x))
#define FOR2(x,y,z) for((x)=(y);(x)<(z);++(x))
#define FORD2(x,y,z) for((x)=(y);(x)>=(z);--(x))
const int maxn = 11;
int x[maxn],n,a[maxn];
int is_sorted(){
        FOR(i,0,n)
                if(a[i] != i + 1)       return 0;
        return 1;
}
int h(){
        int cnt = 0;
        FOR(i,0,n - 1){
                if(a[i] + 1 != a[i + 1])
                        ++cnt;
        }
        return cnt;
}
int dfs(int curcnt,int & maxd){
        //成功返回1,同时结束bfs
        if(curcnt == maxd)      return is_sorted();
        //超过范围
        if(curcnt*3 + h() > 3 * maxd)   return 0;
        int tmp[maxn];
        memcpy(tmp,a,sizeof(int)*n);
        FOR(i,1,n){//枚举长度
                for(int j = 0; i + j - 1 < n;++j){//枚举起点
                        //剪切 区段
                        int t1[maxn],t2[maxn],c1 = -1,c2 = -1;
                        FOR(k,0,n){
                             if( k >= j && k < i + j)  t1[++c1] = tmp[k];
                             else t2[++c2] = tmp[k];
                        }
                        //粘贴区段
                        FOR(k,0,j){
                                int c = -1;
                                FOR(l,0,k)      a[++c] = t2[l];
                                FOR(l,0,c1+1)     a[++c] = t1[l];
                                FOR(l,k,c2+1)     a[++c] = t2[l];
                                //进入下层dfs
                                if(dfs(curcnt + 1,maxd))        return 1;
                        }
                }
        }
        return 0;
}
int main(){
        int cntcase = 0;
        while(~scanf("%d",&n) && n){
                FOR(i,0,n)      scanf("%d",x+i);
                int i;
                //枚举步骤数目,
                for(i = 0;;++i){
                        memcpy(a,x,sizeof(int)*n);
                        if(dfs(0,i))    break;
                }
                printf("Case %d: %d\n",++cntcase,i);
        }
    return 0;
}  






以上是关于[2016-02-27][UVA][11212][Editing a Book]的主要内容,如果未能解决你的问题,请参考以下文章

UVA 11212 Editing a Book [迭代加深搜索IDA*]

Editing a Book UVA - 11212 IDA*

Uva 11212 编辑书稿(迭代加深搜索)

UVa11212 Editing a Book(IDA*)

UVa11212 Editing a Book (IDA*)

Uva11212 Editing a Book(IDA*)