牛客NC60 判断一棵二叉树是否为搜索二叉树和完全二叉树【中等 BFS/DFS Java,Go,PHP】

题目

在这里插入图片描述
题目链接:
https://www.nowcoder.com/practice/f31fc6d3caf24e7f8b4deb5cd9b5fa97

思路

	题目标明用dfs,递归
	本答案用BFS,非递归
	1.判断是否是二叉搜索树,只需要中序遍历,如果不是升序的,那么就不是二叉搜索树
	2.判断是否完全二叉树,只需要层序遍历,检查每一个节点对应的下标是否是递增的,
	如果不是就不是完全二叉树

参考答案Java

import java.util.*;

/*
 * public class TreeNode {
 *   int val = 0;
 *   TreeNode left = null;
 *   TreeNode right = null;
 *   public TreeNode(int val) {
 *     this.val = val;
 *   }
 * }
 */

public class Solution {
    /**
     * 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
     *
     *
     * @param root TreeNode类 the root
     * @return bool布尔型一维数组
     */
    public boolean[] judgeIt (TreeNode root) {
                boolean[] ans = {true, true};
            if (root == null) {
                ans[0] = true;
                ans[1] = true;
                return ans;
            }
            //1.中序遍历,检查是否是搜索二叉树
            Stack<TreeNode> stack = new Stack<>();
            TreeNode prev = null;
            TreeNode cur = root;
            while (!stack.isEmpty() || cur != null) {
                while (cur != null) {
                    stack.add(cur);
                    cur = cur.left;
                }

                cur = stack.pop();
                if (prev != null && cur.val < prev.val) {
                    ans[0] = false;
                    break;
                }
                prev = cur;

                cur = cur.right;
            }


            //2.层序遍历,检查是否是完全二叉树
            //层序遍历,如果是完全二叉树,那么下标是递增的
            cur = root;
            List<TreeNode> q = new ArrayList<>();
            List<Integer> qi = new ArrayList<>();
            q.add(cur);
            qi.add(0);
            int prevIdx = -1;

            while (!q.isEmpty()) {
                int size = q.size();

                List<TreeNode> qnew = new ArrayList<>();
                List<Integer> qinew = new ArrayList<>();

                for (int i = 0; i < size; i++) {
                    TreeNode pop = q.get(i);
                    int idx = qi.get(i);

                    TreeNode left = pop.left;
                    TreeNode right = pop.right;

                    if(prevIdx!=-1 && idx!=prevIdx+1){
                        ans[1]=false;
                        break;
                    }
                    prevIdx = idx;
                    if (left != null) {
                        qnew.add(left);
                        qinew.add(2 * idx + 1);
                    }

                    if (right != null) {
                        qnew.add(right);
                        qinew.add(2 * idx + 2);
                    }
                }

                q = qnew;
                qi = qinew;

            }
            return ans;
    }
}

参考答案Go

package main


import . "nc_tools"

/*
 * type TreeNode struct {
 *   Val int
 *   Left *TreeNode
 *   Right *TreeNode
 * }
 */

/**
 * 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
 *
 *
 * @param root TreeNode类 the root
 * @return bool布尔型一维数组
 */
func judgeIt(root *TreeNode) []bool {
	ans := make([]bool, 2)
	ans[0] = true
	ans[1] = true
	if root == nil {

		return ans
	}

	//第一步:中序遍历检查是否是二叉搜索树
	q := []*TreeNode{}
	prev := 0
	setprev := false
	cur := root
	for len(q) > 0 || cur != nil {
		for cur != nil {
			q = append(q, cur)
			cur = cur.Left
		}

		size := len(q)
		qnew := []*TreeNode{}
		pop := q[size-1]

		if setprev && pop.Val < prev {
			ans[0] = false
			break
		}
		prev = pop.Val
		setprev = true
		for i := 0; i < size-1; i++ {
			qnew = append(qnew, q[i])
		}

		q = qnew
		cur = pop.Right
	}

	//第二步:层序遍历根据坐标关系检查是否是完全二叉树
	cur1 := root
	q1 := []*TreeNode{}
	q1idex := []int{}
	q1 = append(q1, cur1)
	q1idex = append(q1idex, 0)
	prev = 0
	setprev = false
	for len(q1) > 0 {
		size := len(q1)
		q1bak := []*TreeNode{}
		q1idexbak := []int{}

		for j := 0; j < size; j++ {
			pop := q1[j]
			idx := q1idex[j]

			if setprev && idx != prev+1 {
				ans[1] = false
				break
			}
			prev = idx
			setprev = true
			if pop.Left != nil {
				q1bak = append(q1bak, pop.Left)
				q1idexbak = append(q1idexbak, 2*idx+1)
			}

			if pop.Right != nil {
				q1bak = append(q1bak, pop.Right)
				q1idexbak = append(q1idexbak, 2*idx+2)
			}
		}

		if ans[1] == false {
			break
		}

		q1 = q1bak
		q1idex = q1idexbak
	}
	return ans
}

参考答案PHP

<?php

/*class TreeNode{
    var $val;
    var $left = NULL;
    var $right = NULL;
    function __construct($val){
        $this->val = $val;
    }
}*/

/**
 * 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
 *
 * 
 * @param root TreeNode类 the root
 * @return bool布尔型一维数组
 */
function judgeIt( $root )
{
     $ans = [0=>true,1=> true];
    if ($root == null) {
        return $ans;
    }

    $cur = $root;
    //第一步:中序遍历检查是否是二叉搜索树
    $stack = array();
    $prev = null;
    $arrindex = 0;
    while (count($stack) > 0 || $cur != null) {
        while ($cur != null) {
            $stack[$arrindex++] = $cur;
            $cur = $cur->left;
        }

        $size = count($stack);
        $pop = $stack[$size - 1];

        $stacknew = array();
        for ($i = 0; $i < $size - 1; $i++) {
            $stacknew[$i] = $stack[$i];
        }
        $stack = $stacknew;


        if ($prev != null && $prev > $pop->val) {
            $ans[0] = false;
            break;
        }
        $arrindex = $size-1;
        $prev = $pop->val;

        $cur = $pop->right;
    }
    //第二步:层序遍历根据坐标关系检查是否是完全二叉树
    $cur = $root;
    $q = [$cur];
    $qi = [0];
    $prevIdx = null;
    while (count($q) > 0) {

        $size = count($q);
        $qnew = array();
        $qinew = array();
        $arrindex = 0;
        for ($i = 0; $i < $size; $i++) {
            $pop = $q[$i];
            $idx = $qi[$i];

            if ($prevIdx != null && $prevIdx != $idx - 1) {

                $ans[1] = false;
                break;
            }

            $prevIdx = $idx;
            if ($pop->left != null) {
                $qnew[$arrindex] = $pop->left;
                $qinew[$arrindex] = intval(2 * $idx + 1);
                $arrindex++;
            }

            if ($pop->right != null) {
                $qnew[$arrindex] = $pop->right;
                $qinew[$arrindex] = intval(2 * $idx + 2);
                $arrindex++;
            }
        }

        if ($ans[1] == false) {
            break;
        }
        $q = $qnew;
        $qi = $qinew;
    }

    return $ans;
}
  • 7
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

赵长辉

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值