牛客剑指Offer刷题汇总-2020/2/05-JAVA

1.二叉树的深度
个人解析:
这道题很简单,只需要求树的深度,采用递归可以轻松解决。
AC源码:


public class Solution
{
	public int TreeDepth(TreeNode root)
	{
		if(root == null)
			{
				return 0;
			}
		int left = TreeDepth(root.left);
		int right = TreeDepth(root.right);
		return Math.max(left,right)+1;
	}
}

2.平衡二叉树
个人解析:
这道题相当于求二叉树深度的进阶版,同样是采取递归的方式解决。
AC源码:

public class Solution
{
	public boolean IsBalanced_Solution(TreeNode root)
	{
		return getDepth(root) != -1;
	}
	private int getDepth(TreeNode root)
	{
		if(root == null)
			return 0;
		int left = getDepth(root.left);
		if(left == -1)
			return -1;
		int right = getDepth(root.right);
		if(right == -1)
			return -1;
		return Math.abs(left-right)>1? -1 :1+Math.max(left,right);
	}
}

3.和为S的两个数字
个人解析:
由于两个数字的相差绝对值越大,他们的乘积越小,所以采用双指针的方法,一个从头开始,一个从尾开始遍历,有3种情况,
1).x+y=sum就是结果
2).x+y>sum y–
3).x+y<sum x++
AC源码:

import java.util.ArrayList;
public class Solution
{
	public ArrayList<ArrayList<Integer>> FindContinuousSequence(int sum)
	{
		ArrayList<Integer> result =new ArrayList<>();
		int x=0;
		int y=array.length-1;
		while(x<y)
		{
			if(array[x]+array[y])==sum
			{
				result.add(array[x]);
				result.add(array[y]);
				break;
			}
			else if(array[x]+array[y]>sum)
			{
				y--;
			}
			else
			{
				x++;
			}
			}
			return result;
	}
}

4.数组中只出现一次的数字
个人解析:
这题要用到异或的思想,一个数异或他自己本身等于0,所以一开始先将数组中的数都异或一遍,就只剩一个数字了,然后我们从这个数字里面分离出最后答案需要的两个数字。
AC源码:

public class Solution
{
	public void FindNumsAppearOnce(int[] array,int[]num1,int[]num2)
	{
		int length=array.length;
		if(length==2)
		{
			num1[0]=array[0];
			num2[0]=array[1];
			return;
		}
		int bitResult=0;
		for(int i=0;i<length;i++)
			bitResult ^= array[i];
		int index = findFirst1(bitResult);
		for(int i=0;i<length;i++)
		{
			if(isBit1(array[i],index))
				num1[0]^=array[i];
			else
				num2[0]^=array[i];
		}
	}
	private int findFirst1(int bitResult)
	{
		int index=0;
		while(((bitResult&1)==0)&&index<32)
		{
			bitResult >>=1;
			index++;
		}
		return index;
	}
	private boolean isBit1(int target,int index)
	{
		return ((target>>index)&1)==1;
	}
}

5.和为S的连续正数序列
个人解析:
采用动态窗口的想法去解决这道题,两个起点,相当于动态窗口的两边,根据其窗口内的值的和来确定窗口的位置和大小,由于是连续的,差为1的一个序列,那么求和公式是(a0+an)*n/2,相等,那么就将窗口范围的所有数添加进结果集,如果当前窗口内的值之和小于sum,那么右边窗口右移一下,如果当前窗口内的值之和大于sum,那么左边窗口右移一下。
AC源码:

import java.util.ArrayList;
public class Solution {
    public ArrayList<ArrayList<Integer> > FindContinuousSequence(int sum) {
        ArrayList<ArrayList<Integer> > result = new ArrayList<>();
        int plow = 1,phigh = 2;
        while(phigh > plow){
            int cur = (phigh + plow) * (phigh - plow + 1) / 2;
            if(cur == sum){
                ArrayList<Integer> list = new ArrayList<>();
                for(int i=plow;i<=phigh;i++){
                    list.add(i);
                }
                result.add(list);
                plow++;
            }else if(cur < sum){
                phigh++;
            }else{
                plow++;
            }
        }
        return result;
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值