UVA 442 矩阵链乘

这道题情况有点多,整理了好些时候

大方向比较清楚,但细节处理不是很到位

方法基本思想:碰到右括号,则一直弹栈直到乘法做完到左括号,一并弹出

然后把运算结果重新压回栈中

#include <iostream>
#include <sstream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <string>
#include <vector>
#include <set>
#include <cctype>
#include <algorithm>
#include <cmath>
#include <deque>
#include <queue>
#include <map>
#include <stack>
#include <iomanip>
using namespace std;
///
#define INF 0xffffff7
#define maxn 300
///
struct M{
	 char ch;
	int a;
	int b;
};
bool operator != (const M &A, const M &B)
{
	return ((A.a != B.a) || (A.b != B.b));
}
bool operator == (const M &A, const M &B)
{
	return ((A.a == B.a) && (A.b == B.b));
}
M Martrix[maxn];
int main()
{	///
	int i, j;
	string str;
	int n;
	cin >> n;
	for (i = 0; i < n; i++)
	{
		char chc;
		int aa, bb;
		cin >> chc >> aa >> bb;
		Martrix[i].ch = chc;
		Martrix[i].a = aa;
		Martrix[i].b = bb;
	}
	M kh;
	kh.a = 0;
	kh.b = 0;
	while (cin >> str)
	{
		int ans(0);
		bool IsOk = true;
		if (str.size() == 1)
		{
			cout << "0" << endl;
			continue;
		}
		stack<M> stk;
		str.insert(0, "(");
		str.append(")");

		string::iterator it = str.begin();
		while (it != str.end())
		{
			if ((*it) == '(')
			{
				stk.push(kh);
				it++;
			}
			else if ((*it) == ')')
			{
				//如果栈空,则不对
				if (stk.empty())
				{
					IsOk = false;
					break;
				}
				//如果就是左括号
				if (stk.top() == kh)
				{
					stk.pop();
					it++;
					continue;
				}

				//如果是数值矩阵
				while (!stk.empty() && stk.top() != kh)
				{
					//取出数值矩阵
					M mul2;
					mul2.a = stk.top().a;
					mul2.b = stk.top().b;
					stk.pop();

					//如果没有符号了(应该至少有左括号)
					if (stk.empty())
					{
						IsOk = false;
						break;
					}
					//如果左侧是左括号
					if (stk.top() == kh)
					{
						stk.pop();
						stk.push(mul2);
						break;
					}

					//如果乘法不对
					if (stk.top().b != mul2.a)
					{
						IsOk =false;
						break;
					}
					ans += stk.top().a * stk.top().b * mul2.b;
					M temp;
					temp.a = stk.top().a;
					temp.b = mul2.b;
					stk.pop();
					if (stk.empty())
					{
						IsOk = false;
						break;
					}
					if (stk.top() == kh)
					{
						stk.pop();
						stk.push(temp);
						break;
					}
					stk.push(temp);
				}
				it++;
			}
			else
			{
				M temp;
				temp.ch = (*it);
				temp.a = Martrix[(*it) - 'A'].a;
				temp.b = Martrix[(*it) - 'A'].b;
				stk.push(temp);
				it++;
			}
			if (!IsOk)
			{
				break;
			}
		}
		if (IsOk)
		{
			cout << ans << endl;
		}
		else
			cout << "error" << endl;
	}

		
    ///
    return 0;
	
}



 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值