2018.4.21 T3化学题

化学题
【问题描述】
Enos 最近遇到了很多同一类型的题目:计算某个物质的相对分子质
量。他已经对此感到十分厌倦,想请你帮他写个程序来算。
【输入格式】
从文件 chemistry.in 中读入数据。
第一行两个整数 n,m,表示 Enos 已知的元素种数和他要计算的物质
种数。
接下来 n 行,每行包含一个字符串和一个正整数,分别表示 Enos 已
知的这种元素的符号及其相对原子质量。每个字符串长度为 1 或 2,如果
长度为 1,则只包含一个大写字母,否则包含一个大写字母和一个小写字
母。你不必考虑这种元素是否存在及相对原子质量是否准确。
接下来 m 行,每行一个字符串,仅包含字母、数字和括号,表示
Enos 要你帮他计算相对分子质量的物质的化学式,保证化学式合法且其中
的所有元素都已给出。你也不必考虑这些物质是否存在。
【输出格式】
输出到文件 chemistry.out 中。
共 m 行,每行一个整数,表示每种物质的相对分子质量。
【样例输入】
21 5
H 1
He 4
Li 7
Be 9
B 11
C 12
N 14
O 16
F 19
Ne 20
Na 23
Mg 24
Al 27
Si 28
P 31
S 32
Cl 35
Ar 40
K 39
Ca 40
Ac 59
Al2(SO4)3
K2CO3
CH3COONa
(CH2CH2)1000
KAc
【样例输出】
342
138
82
28000
98
【数据规模】
对于 30% 的数据,n ≤ 5 ,
∑︀
|s| ≤ 50;
对于 60% 的数据,n≤ 20 ,
∑︀
|s| ≤ 1 000;
对于 100% 的数据,0 < n ≤ 100 , 0 <
∑︀
|s| ≤ 1 000 000,给出的所
有数字≤ 1 000,答案≤ 10 18 ;
均匀分布着 20% 的数据,所以化学式不包含括号;

均匀分布着 20% 的数据,所有元素符号长度均为 1。

-----------------------------------------------------------------------

本身不难,用栈处理,对于同个()中的每个元素相加,元素后面有数字就相乘

元素储存我用的是map,没hash快

#include <iostream>
#include <cstdio>
#include <string>
#include <map>
using namespace std;
#define LL long long
map<string,LL> x;
int n,m;
string s,a;
LL ans[10000000];//第 p 层括号的值
void chu() {
	LL now=0,p=0;
	ans[0]=0;cin>>a;
	for (int i=0;i<a.size();) {
		if (a[i]=='(') p++,i++,ans[p-1]+=now,now=0;
		if (a[i]==')') p--,i++,now+=ans[p+1],ans[p+1]=0;
		if (a[i]>='A' && a[i]<='Z') {
			ans[p]+=now,now=0;
			s+=a[i];
			if (a[i+1]>='a' && a[i+1]<='z') s+=a[i+1],i++;
			now+=x[s];
			s.clear();
			i++;
		}
		int w=0;
		if (a[i]>='0' && a[i]<='9') {
			while (a[i]>='0' && a[i]<='9') w=w*10+a[i]-'0',i++;
			now*=w;
		}
	}
	ans[0]+=now;
	printf("%lld\n",ans[0]);
}
int main() {
	freopen("chemistry.in","r",stdin);
	freopen("chemistry.out","w",stdout);
	scanf("%d%d",&n,&m);
	for (int i=1,k;i<=n;i++){
		cin>>s>>k;x[s]=k;
	}
	s.clear();
	for (int i=1;i<=m;i++) chu();
	fclose(stdin);fclose(stdout);
}

类似题目点击打开链接

点击打开链接

猜你喜欢

转载自blog.csdn.net/qq_41893580/article/details/80034014
T3