https://vjudge.net/problem/UVA-10618

题目

你想学着玩跳舞机。跳舞机的踏板上有4个箭头:上、下、左、右。当舞曲开始时,屏幕上会有一些箭头往上移动。当向上移动箭头与顶部的箭头模板重合时,你需要用脚踩一下踏板上的相同箭头。不需要踩箭头时,踩箭头并不会受到惩罚,但当需要踩箭头时,必须踩一下,哪怕已经有一只脚放在了该箭头上。很多舞曲的速度快,需要来回倒腾步子,所以最好写一个程序来帮助你选择一个轻松的踩踏方式,使得能量小号最少。

为了简单起见,将一个八分音符作为一个基本时间单位,每个时间单位要么需要踩一个箭头(不会同时需要踩两个箭头),要么什么都不需要踩。在任意时刻,你的左右脚应放在不同的两个箭头上,且每个时间单位内只有一只脚能动(移动和/或踩箭头),不能跳跃。另外,你必须面朝前方以看到屏幕(即:你不能把左脚放在右箭头上,并且右脚放在左箭头上)。当你执行一个动作(移动和/或踩)时,消耗的能量这样计算

(紫书上的说明是错的= =)

Performing an action with a foot costs 1 unit of energy if it did NOT perform an action in the previous time unit. If it did, then it costs 3 units if it doesn't change arrows, 5 units if it moves to an adjacent arrow, and 7 units if it moves directly across the pad (between Up and Down, or Left and Right).

正常情况下,你的左脚不能放到右箭头上(或者反之),但有一种情况例外:如果你的左脚在上箭头或者下箭头,你可以临时扭着身子用右脚踩左箭头,但是在你的右脚移出左箭头之前,你的左脚都不能移到另一个箭头上。类似地,右脚在上箭头或者下箭头时,你也可以临时用左脚踩右箭头。一开始,你的左脚在左箭头上,右脚在右箭头上。

输入包含最多100组数据,每组数据包含一个长度不超过70的字符串,即各个时间单位需要踩的箭头。L和R分别表示左右箭头,“.”表示不需要踩箭头。输出应是一个长度和输入相同的字符串,表示每个时间单位执行动作的脚。L和R分别是左右脚,“.”表示不踩。比如, .RDLU 的最优解是 RLRLR ,第一次是把右脚放在下箭头上。

题解

因为最多只有70个阶段,所以不会爆栈,直接递归,懒得改迭代了= =

设$dp[l][r][t][id]$为时间为$t$,左脚在$l$,右脚在$r$,且上一次移动了(id==1?左:右)脚

很容易写出转移= =

状态和转移最多$\mathcal{O}(lrt\times id) \leqslant 2240$,完全不管时间限制……

紫书上给的能量消耗说明是错的,害得我改了好久= =

AC代码

#include<bits/stdc++.h>
using namespace std; #define REP(r,x,y) for(register int r=(x); r<(y); r++)
#define PER(r,x,y) for(register int r=(x); r>(y); r--)
#define REPE(r,x,y) for(register int r=(x); r<=(y); r++)
#define PERE(r,x,y) for(register int r=(x); r>=(y); r--)
#ifdef sahdsg
#define DBG(...) printf(__VA_ARGS__)
#else
#define DBG(...) (void)0
#endif
#define iabs(a) ((a)<0?(-(a)):(a))
char ops[80];
int d[4][4][80][3];
inline int getnum(int x) {
switch(ops[x]) {
case 'U': return 0;
case 'L': return 1;
case 'D': return 2;
case 'R': return 3;
case '.': return -1;
}
return -1;
} inline bool can(int l, int r, int ll, int lr) {
if(l==r) return false;
if((ll==2 || ll==0) && lr==1 && l!=ll) return false;
if((lr==2 || lr==0) && ll==3 && r!=lr) return false;
if(l==3 && r==1) return false;
return true;
} inline int cost(int f, int t) {
if(f==t) return 3;
if(iabs(f-t)==2) return 7;
return 5;
} int solve(int l, int r, int t, int id) {
if(ops[t]<=' ') return 0;
int &now = d[l][r][t][id];
if(now>=0) return now;
int num=getnum(t); now=0x3f3f3f3f;
if(num>=0) {
if(can(l,num,l,r)) now=min(now,solve(l,num,t+1, 2)+(id==2?cost(r,num):1));
if(can(num,r,l,r)) now=min(now,solve(num,r,t+1, 1)+(id==1?cost(l,num):1));
} else {
REP(i,0,4) {
if(can(l,i,l,r)) now=min(now,solve(l,i,t+1, 2)+(id==2?cost(r,i):1));
if(can(i,r,l,r)) now=min(now,solve(i,r,t+1, 1)+(id==1?cost(l,i):1));
}
now=min(now,solve(l,r,t+1,0));
}
return now;
}
char ans[80];
int ansn=0;
inline void anx(char x) {
ans[ansn++]=x;
}
bool prn(int l, int r, int t, int id) {
if(ops[t]<=' ') return true;
int &now = d[l][r][t][id];
int num=getnum(t);
if(num>=0) {
if(can(l,num,l,r)) if(now==solve(l,num,t+1, 2)+(id==2?cost(r,num):1))
if(prn(l,num,t+1, 2)) {anx('R'); return 1;}
if(can(num,r,l,r)) if(now==solve(num,r,t+1, 1)+(id==1?cost(l,num):1))
if(prn(num,r,t+1, 1)) {anx('L'); return 1;}
} else {
REP(i,0,4) {
if(can(l,i,l,r)) if(now==solve(l,i,t+1, 2)+(id==2?cost(r,i):1))
if(prn(l,i,t+1,2)) {anx('R'); return 1;}
if(can(i,r,l,r)) if(now==solve(i,r,t+1, 1)+(id==1?cost(l,i):1))
if(prn(i,r,t+1,1)) {anx('L'); return 1;}
}
if(now==solve(l,r,t+1,0)) if(prn(l,r,t+1,0)) {anx('.'); return 1;}
}
return now;
} int main() {
#ifdef sahdsg
freopen("in.txt","r",stdin);
#endif
while(1) {
fgets(ops, 80, stdin); if(ops[0]=='#') break;
memset(d,-1,sizeof d); ansn=0;
solve(1,3,0,0); //DBG("%d\n", d[1][3][0][0]);
prn(1,3,0,0);
while(0<ansn--) putchar(ans[ansn]); putchar('\n');
}
return 0;
}

UVA 10618 Tango Tango Insurrection的更多相关文章

  1. 【Uva 10618】Tango Tango Insurrection

    [Link]: [Description] 玩跳舞机. 有一定的约束. 归纳起来就是以下三点 1.两只脚不能同时踩一个位置 2.如果左脚踩在了右键上,那么下一次移动的一定要是左脚 3.如果右脚踩在了左 ...

  2. 【暑假】[深入动态规划]UVa 10618 Tango Tango Insurrection

    UVa 10618 Tango Tango Insurrection 题目: Problem A: Tango Tango Insurrection You are attempting to lea ...

  3. uva 10618 Tango Tango Insurrection 解题报告

    Tango Tango Insurrection Time Limit: 3000MS     64bit IO Format: %lld & %llu Submit Status uDebu ...

  4. 【杂题总汇】UVa-10618 Tango Tango Insurrection

    [UVa-10618] Tango Tango Insurrection ◇ 题目 +vjudge 链接+ (以下选自<算法竞赛入门经典>-刘汝佳,有删改) <题目描述> 你想 ...

  5. 【暑假】[深入动态规划]UVa 10618 Fun Game

    UVa 10618 Fun Game 题目: http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=36035 思路:   一圈人围坐 ...

  6. 【暑假】[深入动态规划]UVa 10618 Fixing the Great Wall

    UVa 10618 Fixing the Great Wall 题目:  http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=361 ...

  7. 【暑假】[深入动态规划]UVa 10618 The Bookcase

    UVa 12099  The Bookcase 题目: http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=42067 思路:    ...

  8. UVa 10618 跳舞机

    https://vjudge.net/problem/UVA-10618 这道题目题意很复杂,代码也是参考了别人的,因为自己实在是写不出.d[i][a][b][s]表示分析到第i个箭头时,此时左脚处于 ...

  9. Getting Started with Google Tango(Google Tango开始教程)

    https://developers.google.com/tango/ Build apps that understand space and motion in high fidelity on ...

随机推荐

  1. 前端面试:谈谈 JS 垃圾回收机制

    摘要: 不是每个人都回答的出来... 最近看到一些面试的回顾,不少有被面试官问到谈谈JS 垃圾回收机制,说实话,面试官会问这个问题,说明他最近看到一些关于 JS 垃圾回收机制的相关的文章,为了 B 格 ...

  2. 少侠学代码系列(一)->JS起源

    少侠:喂,有人吗?赶紧出来接客了,有没有人啊 帅气的我:来了来了,少侠有何吩咐? 少侠:把你们店里的秘籍呈上来我要学JS 帅气的我:少侠,别这样,我们秘籍是不外传的,祖上传下来的规矩,传人妖不传男女. ...

  3. 广州.NET微软技术俱乐部微信群各位技术大牛的blog

    1. .net core和微服务领域的张善友张队长和马洪喜,证明了.net core和微服务已经在各方面都不比java差2. Xamarin的卢建晖,证明了.net在移动开发领域也是很牛的.3. wi ...

  4. pthread_once()函数详解

    转自:pthread_once()函数详解 pthread_once()函数详解   在多线程环境中,有些事仅需要执行一次.通常当初始化应用程序时,可以比较容易地将其放在main函数中.但当你写一个库 ...

  5. mysql免安装版初次使用

    在自己电脑上安装一个mysql数据库并启动,碰到一些问题,总结一下 1.下载免安装版mysql数据库,百度下载了了5.7.25版本 2.在bin文件夹下找到my-defaults.ini文件,我这没有 ...

  6. Task.Wait and “Inlining”

    “What does Task.Wait do?” Simple question, right? At a high-level, yes, the method achieves what its ...

  7. Spring Boot 2.x 快速入门(上)HelloWorld示例

    本文重点 最近决定重新实践下Spring Boot的知识体系,因为在项目中遇到的总是根据业务需求走的知识点,并不能覆盖Spring Boot完整的知识体系,甚至没有一个完整的实践去实践某个知识点.最好 ...

  8. 【Python 10】汇率兑换3.0(while循环)

    1.案例描述 设计一个汇率换算程序,其功能是将美元换算成人民币,或者相反. 2.0增加功能:根据输入判断是人民币还是美元,进行相应的转换计算 3.0增加功能:程序可以一直运行,知道用户选择退出 2.案 ...

  9. Centos安装php php-fpm 以及 配置nginx

    下载php源码包 http://www.php.net/downloads.php 安装php .tar.bz2 cd php- ./configure --prefix=/usr/local/php ...

  10. Java线程状态转换

    前言:对于Java线程状态方面的知识点,笔者总感觉朦朦胧胧,趁着最近整理资料,将Java线程状态方面的知识点总结归纳,以便加深记忆. 1.Java线程状态值 在Thread类源码中通过枚举为线程定义了 ...