一些主要城市拥有树形的地铁系统,即在任何一对车站之间,有且只有一种方式可以乘坐地铁。
此外,这些城市大多数都有一个中央车站。
想象一下,你是一名在拥有树形地铁系统的城市游玩的游客,你想探索该城市完整的地铁线路。
你从中央车站出发,随机选择一条地铁线,然后乘坐地铁行进。
每次到达一个车站,你都将选择一条尚未乘坐过的地铁线路进行乘坐。
如果不存在未乘坐过的线路,则退回到上一个车站,再做选择。
直到你将所有地铁线路都乘坐过两次(往返各一次),此时你将回到中央车站。
之后,你以一种特殊的方式回忆自己的坐车过程,你将你的完整地铁乘坐路线编码为一个二进制字符串。
其中 00 编码表示你乘坐地铁线路到达距离中央车站更远的一站,11 编码表示你乘坐地铁线路到达距离中央车站更近的一站。
输入格式
第一行输入一个正整数 nn,代表测试用例数量。
每个测试用例由两行组成,每行输入一个由字符 00 和 11 构成的字符串,长度最多为 30003000, 两个字符串都描述了一种树形地铁系统的正确探索路线。
输出格式
对于每个测试用例,如果两个字符串描述的探索路线可以视为同一个地铁系统的两种探索路线,则输出
same
。否则,输出
different
。每行输出一个结果。
输入样例:
2 0010011101001011 0100011011001011 0100101100100111 0011000111010101
输出样例:
same different
性质:若两课数同构,则说明他们的最小表示相同;
所以我们只要求得两棵树的最小表示,若相同则说明他们是同构的
#include <cstdio>
#include <vector>
#include <iostream>
#include <algorithm>
using namespace std;
string get(string &str, int &u)
{
u ++ ;//记住这里跳过了下去的时候的0;
vector<string> ans;
while (str[u] == '0') ans.push_back(get(str, u));
u ++ ;//为求最小表示,先除去往上走的节点,将其放在最后。
string res = "0";//加上下去的时候的0
sort(ans.begin(), ans.end());
for (auto s : ans) res += s;//加上他的所有子树的最小表示
res += '1';//把除去的往上走的节点加上;
return res;
}
int main()
{
int T;
cin >> T;
while (T -- )
{
string a, b;
cin >> a >> b;
a = '0' + a + '1';//给根节点加一条边,设置边界
b = '0' + b + '1';
int as = 0, bs = 0;
if (get(a, as) == get(b, bs)) puts("same");
else puts("different");
}
return 0;
}