题意:输入n个矩阵的维度和一些矩阵链乘表达式,输出乘法的次数。如果乘法无法进行,输出error。假定A是m*n,B是n*p的矩阵,那么A*B是m*p矩阵,乘法次数为m*n*p。假定A的列数不等于B的行数,则乘法无法进行。
例如,A是50*10的,B是10*20的,C是20*5的,则(A(BC))的乘法次数为10*20*5(BC的乘法次数)+50*10*5((A(BC)))的乘法次数 = 3500
分析:本题的关键是解析表达式。本题的表达式比较简单,可以用一个栈来完成:遇到字母时入栈,遇到右括号时出栈并计算,然后结果入栈。因为输入保证合法,括号无需入栈。
以上内容来自算法竞赛入门经典。
补充:如果碰到右括号那么就拿出两个元素计算,计算结果放回去,模拟即可。
#include<bits/stdc++.h>
using namespace std;
int n;
char str[1005];
struct Matrix
{
int r, c;
Matrix(int _r = 0, int _c = 0): r(_r), c(_c) {}
}a[26];
int main()
{
scanf("%d", &n);
for (int i = 0; i < n; i++)
{
scanf("%s", str);
int id = str[0] - 'A';
scanf("%d%d", &a[id].r, &a[id].c);
}
while (~scanf("%s", str))
{
int ans = 0, len = strlen(str);
stack<Matrix> S;
for (int i = 0; i < len; i++)
{
if (isalpha(str[i])) S.push(a[str[i]-'A']);
else if (str[i] == ')')
{
Matrix m2 = S.top(); S.pop();
Matrix m1 = S.top(); S.pop();
if (m1.c != m2.r) { ans = -1; break; }
ans += m1.r * m1.c * m2.c;
S.push(Matrix(m1.r, m2.c));
}
}
if (ans == -1) printf("error\n");
else printf("%d\n", ans);
}
return 0;
}