虽然在上边写了二叉树但是确实不关二叉树的事情。
这是一个关于天平平衡以及要不要改动的问题。
乍看其实是简单的,但是渐渐会发现这东西和我的代码一样,牵一发动全身(= =|||)。
我第一个想法是找到第一个叶子,然后和边上的比,那么问题来了,如果不一样改哪个叶子,都改?绝对超时鸭。
再想,从下到上,每一个合起来的重量和边上的比,看起来好像靠谱很多,但是问题又来了,叶子很多的时候,再统一就很多,我们假设这是一棵完美二叉树,这个时候可以统计叶子上最多的数字,如果123456呢?一样的超时。
然后就怎么也想不到了。
一心只有暴力……
看了大佬的博客,不妨固定一个,看一下整体会是多重。
然后d层深的节点,有w重,那么这个节点只要不变,那么整体就是w*pow(2*d)重,我数学差没法证明,有会的小伙伴可以在评论帮帮我(= =|||),稍稍可以理解,因为后一层的节点的和一定会是上一层的和,只是分的散和是一样的……
然后问题又来了,我处理不了括号,因为和深度有关,所以深度是必要的。
纠结了半天还是照着博客的写了,博客的明明也没有高深异常,但就是想不到纠结……
再想想其他的……
#include <iostream>
#include <cstring>
#include <cmath>
#include <string>
#include <map>
using namespace std;
int all;
string t;
map<long long, int>m;
void dfs(int l, int r,int deep)
{
if (t[l]=='[')
{
int p = 0;
for (int i = l + 1; i < r; i++)
{
if (t[i] == '[')
p++;
else if (t[i] == ']')
p--;
if (p == 0 && t[i] == ',')
{
dfs(l + 1, i - 1, deep + 1);
dfs(i + 1, r - 1, deep + 1);
}
}
}
else
{
long long sum = 0;
for(int i = l; i <= r; i++)
{
sum *= 10;
sum += (t[i] - '0');
}
sum = sum * pow(2, deep);
m[sum]++;
all++;
}
}
int max(int a, int b)
{
return a > b ? a : b;
}
int main()
{
int T;
cin >> T;
while (T--)
{
m.clear();
cin >> t;
all = 0;
dfs(0, t.length() - 1, 0);
map<long long, int>::iterator it;
int maxn = -1;
for (it = m.begin(); it != m.end(); it++)
{
maxn = max(maxn, it->second);
}
cout << all - maxn << endl;
}
//system("pause");
return 0;
}