题目来源:

点击打开链接

题目翻译:

矩阵乘法问题是动态规划的典型例子。

假设你必须评估一个表达式,如A * B * C * D * E,其中A,B,C,D和E是矩阵。由于矩阵乘法是关联的,乘法运算的次序是任意的。但是,所需的基本乘法的数量很大程度上取决于您选择的评估顺序。 例如,设A是50 * 10矩阵,B是10 * 20矩阵,C是20 * 5矩阵。 计算A * B * C有两种不同的策略,即(A * B)* C和A *(B * C)。 第一个需要15000次基本乘法,但第二个只需要3500次。

你的工作是编写一个程序来确定给定评估策略所需的基本乘法的数量。

输入:

输入由两部分组成:矩阵列表和表达式列表。 输入文件的第一行包含一个整数n(1 <= n <= 26),表示第一部分中的矩阵数量。接下来的n行包含一个大写字母,指定矩阵的名称和两个整数,指定矩阵的行数和列数。 输入文件的第二部分严格遵守以下语法:

SecondPart = Line { Line } <EOF>
Line = Expression <CR>
Expression = Matrix | "(" Expression Expression ")"
Matrix = "A" | "B" | "C" | ... | "X" | "Y" | "Z"

输出:

对于在输入文件的第二部分中找到的每个表达式,如果由于不匹配的矩阵导致表达式的评估导致错误,则输出包含单词“error”的一行。否则,按照括号中指定的方式打印一行,其中包含评估表达式所需的基本乘法数。

例子:

输入

9
A 50 10
B 10 20
C 20 5
D 30 35
E 35 15
F 15 5
G 5 10
H 10 20
I 20 25
A
B
C
(AA)
(AB)
(AC)
(A(BC))
((AB)C)
(((((DE)F)G)H)I)
(D(E(F(G(HI)))))
((D(EF))((GH)I))

输出

0
0
0
error
10000
error
3500
15000
40500
47500
15125

解题:

此题,我用了stack和vector。首先定义一个矩阵结构,此结构包含两个数据:行数和列数。然后定义一个大小为26的矩阵数组,并且按ABC...这样排下去。根据输入改写数组里相应位置的数据;如:输入矩阵A的行列数,则修改vector[0]中的行列数。完成矩阵行列数的存储之后,就用stack来处理计算式子。逐一读取计算式子的字符,遇到字母就进栈,遇到左括号就什么事都不做,遇到右括号就出栈,然后进行计算判断。具体如下:

/*
c++/accepted
*/ #include<iostream>
#include<stack>
#include<string>
#include<vector>
using namespace std; struct rc //定义矩阵结构
{
int r;
int c;
}; int main() {
stack<rc> st1; //栈
vector<rc> vec; //数组
for (int k = 0;k<26;k++) //申请长度为26的矩阵数组
{
rc myrc;
vec.push_back(myrc);
}
int n;
cin >> n;
while (n--)
{
int a, b;
char ch;
cin >> ch; //矩阵名字
cin >> a >> b;
vec[(int)(ch) - 65].r = a; //把行列数存到相应位置的矩阵那,A为vec[0],B为vec[1],以此类推
vec[(int)(ch) - 65].c = b;
}
string s;//输入计算式子
//cin >> s;
while (cin>>s)
{
int num = 0;
if (s.length() == 1)//如果计算式子长度为1,则相乘次数为0
cout << 0 << endl;
else
{
for (int i = 0;i<s.length();i++)
{
if (s[i] >='A'&&s[i]<='Z') //遇到字母就进栈
st1.push(vec[(int)(s[i]) - 65]); else if (s[i] == ')') //遇到右括号,出栈两个
{
rc myrc1 = st1.top();
st1.pop();
rc myrc2 = st1.top();
st1.pop();
if (myrc2.c != myrc1.r)//判断前面矩阵的列数是否等于后面矩阵的行数,如果不等,则error
{
cout << "error" << endl;
num = 0;
break;
}
else //如果相等,就计算相乘次数(前行*前列*后列)
{
num = num + myrc2.r*myrc2.c*myrc1.c; //总次数=现次数+此次计算的次数
myrc2.c = myrc1.c;
rc myrc3;//经过一次计算后的结果矩阵(中间矩阵)
myrc3.r = myrc2.r;
myrc3.c = myrc1.c;
st1.push(myrc3);//把中间矩阵进栈
}
}
else//遇到左括号则什么都不做
;
}
}
if (num > 0) //如果num为0,则可能为错,可能已经输出了(0)
cout << num << endl;
}
return 0;
}

ACM解题之(ZOJ 1094) Matrix Chain Multiplication的更多相关文章

  1. ACM学习历程——UVA442 Matrix Chain Multiplication(栈)

    Description   Matrix Chain Multiplication  Matrix Chain Multiplication  Suppose you have to evaluate ...

  2. Matrix Chain Multiplication(表达式求值用栈操作)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1082 Matrix Chain Multiplication Time Limit: 2000/100 ...

  3. Matrix Chain Multiplication[HDU1082]

    Matrix Chain Multiplication Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (J ...

  4. UVA 442 二十 Matrix Chain Multiplication

    Matrix Chain Multiplication Time Limit:3000MS     Memory Limit:0KB     64bit IO Format:%lld & %l ...

  5. 例题6-3 Matrix Chain Multiplication ,Uva 442

    这个题思路没有任何问题,但还是做了近三个小时,其中2个多小时调试 得到的经验有以下几点: 一定学会调试,掌握输出中间量的技巧,加强gdb调试的学习 有时候代码不对,得到的结果却是对的(之后总结以下常见 ...

  6. UVa442 Matrix Chain Multiplication

    // UVa442 Matrix Chain Multiplication // 题意:输入n个矩阵的维度和一些矩阵链乘表达式,输出乘法的次数.假定A和m*n的,B是n*p的,那么AB是m*p的,乘法 ...

  7. UVa 442 Matrix Chain Multiplication(矩阵链,模拟栈)

    意甲冠军  由于矩阵乘法计算链表达的数量,需要的计算  后的电流等于行的矩阵的矩阵的列数  他们乘足够的人才  非法输出error 输入是严格合法的  即使仅仅有两个相乘也会用括号括起来  并且括号中 ...

  8. UVA——442 Matrix Chain Multiplication

    442 Matrix Chain MultiplicationSuppose you have to evaluate an expression like A*B*C*D*E where A,B,C ...

  9. uva-442 Matrix Chain Multiplication

    Suppose you have to evaluate an expression like A*B*C*D*E where A,B,C,D and E are matrices. Since ma ...

随机推荐

  1. 【Java集合源代码剖析】Java集合框架

    转载轻注明出处:http://blog.csdn.net/ns_code/article/details/35564663 Java集合工具包位于Java.util包下,包括了非常多经常使用的数据结构 ...

  2. [转]js 获取浏览器高度和宽度值(多浏览器)(js获取宽度高度大全)

    IE中: document.body.clientWidth ==> BODY对象宽度 document.body.clientHeight ==> BODY对象高度 document.d ...

  3. C# 网络打印机ESC指令打印小票

    public void SendSocketMsg(String ip, int port, int times, byte[] data) { try { byte[] mData; ) { mDa ...

  4. 74. First Bad Version 【medium】

    74. First Bad Version [medium] The code base version is an integer start from 1 to n. One day, someo ...

  5. static关键字 综合小应用

    package unit4; import com.sun.java_cup.internal.version; public class Voter { private static int MAX ...

  6. vue 深入响应式原理

    vue最显著的特性就是不太引人注意的响应式系统(reactivity system),模型层(model)只是普通的javascript对象,修改它则更新视图view.这会让状态管理变得非常简单且直观 ...

  7. Windows中搭建ftp服务器

    使用工具Quick Easy FTP Server Windows中搭建FTP服务器有什么用呢? 确实没有用,直到有一次,我在VM中安装了Linux虚拟机,但是文件怎么也上传不到这个虚拟机中. 然后用 ...

  8. Linux Linux程序练习二

    /* 编写一个程序读取a.txt文件,将文件内容数字从小到大排序,并将排序结果写入b.txt. */ #include <stdio.h> #include <stdlib.h> ...

  9. Win10中配置jdk之后javac无法运行

    环境变量(environment variables)一般是指在操作系统中用来指定操作系统运行环境的一些参数,如:临时文件夹位置和系统文件夹位置等. 环境变量是在操作系统中一个具有特定名字的对象,它包 ...

  10. Python Socket 网络编程 (服务器端编程)

    服务器端主要做以下工作: 打开 socket 绑定到特定的地址以及端口上 监听连接 建立连接 接收/发送数据 上面已经介绍了如何创建 socket 了,下面一步是绑定. 绑定 socket 函数 bi ...