剑指offer<3、4、5、6、7>

一、剑指offer 03.数组中的重复数字

  • 剑指 Offer 03. 数组中重复的数字
    在一个长度为 n 的数组 nums 里的所有数字都在 0~n-1 的范围内。数组中某些数字是重复的,但不知道有几个数字重复了,也不知道每个数字重复了几次。请找出数组中任意一个重复的数字。
    在这里插入图片描述
  • 解题思路
    1、采用HashSet,因为它不允许元素重复
    2、HashSet中的add方法,当添加元素集合中没有该元素时才添加并返回true
    3、当add方法返回值为false时说明该元素重复了,即找到了重复数字
class Solution {
    public int findRepeatNumber(int[] nums) {
        int res=-1; //用来记录重复的数字,因为所有数都是0~n-1,所以初始化为-1
        Set <Integer> set=new HashSet<Integer>();//因为HashSet中不允许元素重复
        for(int num:nums){   //遍历数组  
            if(!set.add(num)){  //HashSet中的add方法 添加成功返回true  添加失败返回false
                res=num;        //添加失败说明该数字重复  将数字赋值给res 
                break;          //找到重复数字结束遍历
            }
        }
        return res; //返回重复数字
    }
}

二、剑指offer 04.二维数组中的查找

  • 剑指 Offer 04. 二维数组中的查找
    在一个 n * m 的二维数组中,每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序。请完成一个高效的函数,输入这样的一个二维数组和一个整数,判断数组中是否含有该整数。
    在这里插入图片描述
  • 解题思路
    在这里插入图片描述
class Solution {
    public boolean findNumberIn2DArray(int[][] matrix, int target) {
        //先判空 若为空格则返回false
        if((matrix==null||matrix.length==0)||(matrix.length==1 && matrix[0].length==0))
            return false;
        int i=0;
        int j=matrix[0].length-1;//对应右上角
        while(i<=matrix.length-1 && j>=0){    //判断便捷
            if(target==matrix[i][j]) return true; //若a[i][j]==target 则返回true
            if(target<matrix[i][j]) j--;         //若target<a[i][j]右上角  则第j列不用看  j--
            else if(target>matrix[i][j]) i++;    若target>a[i][j]右上角  则第i行不用看  i++
        }
        return false;  //若二维数组找完没有返回true ,即为没有该数字 返回false
    }
}

三、剑指offer 05.替换空格

  • 剑指 Offer 05. 替换空格
    请实现一个函数,把字符串 s 中的每个空格替换成"%20"。
    在这里插入图片描述
    -解题思路
    1.创建一个字符数组将结果先放入字符数组(因为要遍历字符串 charAt()方法返回的是字符串),最后再将字符数组转为字符串
    2.创建一个大小为n3的字符数组,因为一个空格换三个字符 所以长度为n 的字符串最多需要的数组长度为n3
    3.创建一个可存放字符的数组小标size ,从0开始
    4.遍历数组,若为空格则将‘%20’放入size下标对应得字符数组中,若不是则将该字符放入字符数组(记得size++)
    5.将字符数组转为字符串,并返回
class Solution {
    public String replaceSpace(String s) {
        int n=s.length();
        //结果先放在char 数组中 因为一个空格换三个字符 所以长度为n 的字符串最多需要的数组长度为n*3
        char [] array=new char[n*3];  
        int size=0;//可存放字符的数组下标
        for(int i=0;i<n;i++){ //遍历字符串
            char c=s.charAt(i);
            if(c==' '){  //若为空格则替换 为
                array[size++]='%';
                array[size++]='2';
                array[size++]='0';
            }else{       //若不为则不需替换直接将c放入数组
                array[size++]=c;
            }
        }
        String news=new String (array,0,size); //最后将字符数组转换为字符串
        return news;  //返回字符串
    }
}

利用String内置函数也可以解

class Solution {
    public String replaceSpace(String s) {
        return s.replace(" ","%20");
    }
}

四、剑指offer 06.从尾到头打印链表

  • 剑指 Offer 06. 从尾到头打印链表
    输入一个链表的头节点,从尾到头反过来返回每个节点的值(用数组返回)。
    在这里插入图片描述
  • 解题思路
    1.因为栈先入后出,所以使用栈
    2.遍历链表,将他们压栈
    3.创建数组,将出栈的值放入数组
    4.返回数组
/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode(int x) { val = x; }
 * }
 */
class Solution {
    public int[] reversePrint(ListNode head) {
        //压栈
        Stack<ListNode> stk=new Stack<>();//创建一个栈
        ListNode temp=head;
        while(temp!=null){
            stk.push(temp);  //循环链表进行压栈
            temp=temp.next;
        }
        int res[]=new int [stk.size()]; //因为返回值为数组
        int size=stk.size();   //获取res大小方便遍历  因为pop每次size都会变小
        for(int i=0;i<size;i++){
            res[i]=stk.pop().val;   //出栈将数值给res[i]
        }
        return res;
       
    }
}

五、剑指offer 07.重建二叉树

  • 剑指 Offer 07. 重建二叉树 剑指 Offer 07. 重建二叉树
    输入某二叉树的前序遍历和中序遍历的结果,请构建该二叉树并返回其根节点。
    假设输入的前序遍历和中序遍历的结果中都不含重复的数字。
    在这里插入图片描述
  • 解题思路
    在这里插入图片描述
/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode(int x) { val = x; }
 * }
 */
class Solution {
    HashMap<Integer,Integer> inmap=new HashMap<>();//标记中序遍历
    int [] pre;//保留的先序遍历
    public TreeNode buildTree(int[] preorder, int[] inorder) {
        pre= preorder;
        for(int i=0;i<inorder.length;i++){
            inmap.put(inorder[i],i);//根据这个值找到中序遍历的下标索引
        }
        return  helper(0,0,inorder.length-1);
    }
    //先序遍历索引,中序遍历左边界  ,中序遍历右边界
    public TreeNode helper(int pre_root,int in_left,int in_right){
        if(in_left>in_right) return null;

        TreeNode node =new TreeNode(pre[pre_root]);
        int i=inmap.get(pre[pre_root]);//根据值获取中序遍历的位置

        //先序遍历索引,中序遍历左边界  ,中序遍历右边界  如表
        node.left=helper(pre_root+1,in_left,i-1);
        node.right=helper(pre_root+i-in_left+1,i+1,in_right);
        return node;

    }
}
  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值