UVA 12166
题目
思路
首先很明显,这个是一个基于二叉树的一个题目,(尽管最后和二叉树没啥关系),那么我们要通过字符串去构造一个二叉树的模型出来,通过观察很容易发现,【符号就是新的一层,所以遇到【符号的时候我们开始构建下一层的子树,遇到】我们就返回上一层进行操作。
我曾经想用递归的方法去求修改的最小个数,后来一直没有解决,最后发现,只要我们确认了任一个叶子结点的权值,那么整个树每一个节点的权值就会定下来,因为父亲节点的权值一定是子结点的两倍,而同一个父节点的子结点权值相同。所以只要有一个结点确定,整个树所有结点权值就确定,因此我们对每一个结点进行统计,看看假设如果这个结点确定了那么树的根结点权值会是多少,最后我们用map存信息,map<定下某个节点之后的整个树的根结点权值,个数>,找到个数最多的即可
代码
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
map<ll, int> m;
int main()
{
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
int t;
string op;
cin >> t;
while(t--)
{
cin >> op;
m.clear();
int dep = 0;
int sum = 0;
int mmax = -1;
for(int i = 0; i < op.size(); i++)
{
char tmp = op[i];
if(op[i] == '[')
{
dep++;
}
else if(op[i] == ']')
{
dep--;
}
else if(op[i] == ',') continue;
else
{
ll num = 0;
int j;
for(j = i; isdigit(op[j]); j++)
{
num = num * 10 + op[j] - '0';
}
i = j - 1;
sum++;
num <<= dep;
m[num]++;
mmax = max(mmax, m[num]);
}
}
cout << sum - mmax << endl;
}
}