UVA - 656 Optimal Programs

来源:互联网 发布:小可知乎 编辑:程序博客网 时间:2024/05/17 03:22

题目大意:给出两个序列,要求找出一个函数 f(x) = y,xi 与 yi 分别对应两个序列中的第 i 个元素,输出函数的操作步骤,要求最短,且按照字典序输出。

解题思路:递归枚举 x0 到 y0 的可能步骤,然后判断其他是否全部满足。


#include <cstdio>#include <stack>#include <cmath>using namespace std;int T, n, ans, start[15], end[15], rec[20], path[20];char str[5][5] = {"ADD", "DIV", "DUP", "MUL", "SUB"};stack <int> S;void init() {    ans = 11;     for (int i = 0; i < n; i++)        scanf("%d", &start[i]);    for (int i = 0; i < n; i++)        scanf("%d", &end[i]);}bool judge(int cur) {    for (int i = 1; i < n; i++) {        stack <int> SS;        SS.push(start[i]);        for (int j = 0; j < cur; j++) {            int a = SS.top(), b;            if (abs(a) > 30000 || (rec[j] == 1 && a == 0))                return false;            if (rec[j] != 2) {                SS.pop();                b = SS.top();                 SS.pop();            }            switch (rec[j]) {                case 0: SS.push(a + b); break;                case 1: SS.push(b / a); break;                case 2: SS.push(a); break;                case 3: SS.push(a * b); break;                case 4: SS.push(b - a); break;            }        }        if (SS.top() != end[i])            return false;    }    return true;}void DFS(int cur, int DUP) {    if (S.top() == end[0] && ans > cur && judge(cur)) {        ans = cur;        for (int i = 0; i < cur; i++)            path[i] = rec[i];        return;    }    if (cur == ans - 1 || abs(S.top()) > 30000)        return;    if (S.size() > 1) {        int a = S.top(); S.pop();        int b = S.top(); S.pop();        rec[cur] = 0;        S.push(a + b);        DFS(cur + 1, DUP);        S.pop();        if (a != 0) {            rec[cur] = 1;            S.push(b / a);            DFS(cur + 1, DUP);            S.pop();        }        S.push(b);        S.push(a);    }    if (DUP < 5) {        rec[cur] = 2;        S.push(S.top());        DFS(cur + 1, DUP + 1);        S.pop();    }    if (S.size() > 1) {        int a = S.top(); S.pop();        int b = S.top(); S.pop();        rec[cur] = 3;        S.push(a * b);        DFS(cur + 1, DUP);        S.pop();        rec[cur] = 4;        S.push(b - a);        DFS(cur + 1, DUP);        S.pop();        S.push(b);        S.push(a);    }}void put() {    printf("Program %d\n", ++T);    if (ans == 0)        puts("Empty sequence\n");    else if (ans == 11)        puts("Impossible\n");    else {        for (int i = 0; i < ans - 1; i++)            printf("%s ", str[path[i]]);        printf("%s\n\n", str[path[ans-1]]);    }}int main() {    while (scanf("%d", &n), n) {        init();        S.push(start[0]);        DFS(0, 0);        S.pop();        put();    }    return 0;}
0 0
原创粉丝点击