872. 叶子相似的树
请考虑一棵二叉树上所有的叶子,这些叶子的值按从左到右的顺序排列形成一个 叶值序列 。
举个例子,如上图所示,给定一棵叶值序列为 (6, 7, 4, 9, 8) 的树。
如果有两棵二叉树的叶值序列是相同,那么我们就认为它们是 叶相似 的。
如果给定的两个根结点分别为 root1 和 root2 的树是叶相似的,则返回 true;否则返回 false 。
示例 1:
解法一、递归
深度优先搜索的顺序就是本题叶值序列的顺序
class Solution {
List<Integer> res;
public boolean leafSimilar(TreeNode root1, TreeNode root2) {
res = new ArrayList<>();
dfs(root1);
dfs(root2);
return validate();
}
public void dfs(TreeNode root){
if(root.left==null&&root.right==null){
res.add(root.val);
return;
}
if(root.left != null) dfs(root.left);
if(root.right != null) dfs(root.right);
}
public boolean validate(){
if(res.size()%2!=0) return false;
int first = 0, second = res.size()/2;
for(;second < res.size();++second,++first){
if(res.get(first)!=res.get(second)) return false;
}
return true;
}
}
解法二、迭代
迭代就是深度优先搜索的非递归版本用deque来维护结点顺序。
class Solution {
public boolean leafSimilar(TreeNode t1, TreeNode t2) {
List<Integer> l1 = new ArrayList<>(), l2 = new ArrayList<>();
process(t1, l1);
process(t2, l2);
if (l1.size() == l2.size()) {
for (int i = 0; i < l1.size(); i++) {
if (!l1.get(i).equals(l2.get(i))) return false;
}
return true;
}
return false;
}
void process(TreeNode root, List<Integer> list) {
Deque<TreeNode> d = new ArrayDeque<>();
while (root != null || !d.isEmpty()) {
while (root != null) {
d.addLast(root);
root = root.left;
}
root = d.pollLast();
if (root.left == null && root.right == null) list.add(root.val);
root = root.right;
}
}
}
解法三、 直接利用一个校验和表示是否相同.
看的评论,tmp=1117 不知道为啥,试了几个别的数就过不了了。
class Solution {
int v1 = 0;
int v2 = 0;
int tmp = 1117;
public boolean leafSimilar(TreeNode root1, TreeNode root2) {
dfs(root1, 1);
dfs(root2, 2);
return v1 == v2;
}
public void dfs(TreeNode root,int index){
if(root.left==null&&root.right==null){
if(index == 1){
v1 += tmp;
v1 ^= root.val;
}else{
v2 += tmp;
v2 ^= root.val;
}
}
if(root.left != null) dfs(root.left,index);
if(root.right != null) dfs(root.right,index);
}
}
解法三、中序(双百)
中序没什么特别的,双百的原因是arr1和arr2的比较。
class Solution {
//ArrayList存储叶子节点
private ArrayList<Integer> arr1 = new ArrayList<>();
private ArrayList<Integer> arr2 = new ArrayList<>();
//中序遍历求从左到右的叶子节点值
public void midOrderImprovement(TreeNode root, List<Integer> list){
if(root != null){
midOrderImprovement(root.left, list);
if(root.left == null && root.right == null){
list.add(root.val);
}
midOrderImprovement(root.right, list);
}
}
//返回arr1和arr2的比较值
public boolean leafSimilar(TreeNode root1, TreeNode root2) {
midOrderImprovement(root1, arr1);
midOrderImprovement(root2, arr2);
return arr1.equals(arr2);
}
}