题目描述
- 给定一个化学式formula(作为字符串),返回每种原子的数量。
- 原子总是以一个大写字母开始,接着跟随0个或任意个小写字母,表示原子的名字。
- 如果数量大于 1,原子后会跟着数字表示原子的数量。如果数量等于 1 则不会跟数字。例如,H2O 和 H2O2 是可行的,但 H1O2这个表达是不可行的。
- 两个化学式连在一起是新的化学式。例如 H2O2He3Mg4 也是化学式。
- 一个括号中的化学式和数字(可选择性添加)也是化学式。例如 (H2O2) 和 (H2O2)3 是化学式。
- 给定一个化学式 formula ,返回所有原子的数量。格式为:第一个(按字典序)原子的名字,跟着它的数量(如果数量大于
1),然后是第二个原子的名字(按字典序),跟着它的数量(如果数量大于 1),以此类推。
例子
示例1:
输入:formula = "H2O"
输出:"H2O"
解释:
原子的数量是 {'H': 2, 'O': 1}。
示例2:
输入:formula = "Mg(OH)2"
输出:"H2MgO2"
解释:
原子的数量是 {'H': 2, 'Mg': 1, 'O': 2}。
示例3:
输入:formula = "K4(ON(SO3)2)2"
输出:"K4N2O14S4"
解释:
原子的数量是 {'K': 4, 'N': 2, 'O': 14, 'S': 4}。
解题思路
1. 按照哪个顺序扫描字符串呢?
看到括号肯定想到是用栈的形式储存右括号后的数字,那么正序遍历字符串就无法直接得到括号内元素的具体个数。
因此我们应选择逆序遍历字符串
2. 该如果保存右括号的数?
先来看一个例子
从图中可以看出先扫描的右括号后被消除,这个规律是不是很像栈?
每扫描到一个右括号我们就把括号后面的数压入栈,每扫描到一个左括号我们就把对栈进行一个pop。
3.什么时候该暂停扫描,计算元素的数量?
字符串里有什么?
- 数字
- 大写字母
- 小写字母
- 左右括号
事实上题中明确说明每个元素首部都是大写字母,且一个元素只有是首部是大写字母。
那么说明读取到大写字母时将我们temp字符串取出计算就行,计算完后temp字符串重置为空。
(temp字符串是我们用于暂时保存扫描过的元素的字符串,应在扫描开始时定义,在计算一次后及时重置)
(读到除左、右括号,或者括号后的数字以为的字符时都该将其添加到temp的首部 #逆序扫描)
4.如何计算元素的数量?
首先通过逆序遍历temp字符串,得到后面的数字,并由string类型转为int类型,记为A
访问栈,并将栈内所有的数相乘,记为B
A与B相乘便是该元素的数量,将其保存在哈希表中
代码
Python实现,代码写的略杂,欢迎指点
class Solution:
def countOfAtoms(self, formula: str) -> str:
numbers = dict()
point = len(formula) - 1
temp = ""
temp_ji = 1
num = [1]
while point >= 0: