力扣100题——杂题

news2026/4/2 16:29:31

回溯——分割回文串

题目

131. 分割回文串 - 力扣(LeetCode)

思路

问题拆解

  • 回文串定义:回文串是指从前往后和从后往前读都是相同的字符串。例如,"aba" 和 "racecar" 都是回文串。

  • 递归 + 回溯思想:我们可以逐步检查字符串的每一个前缀是否是回文串,如果是回文串,则将其作为一个可能的子串继续进行递归,检查剩余部分字符串的可能性。我们需要将所有可能的分割方案保存下来。

  • 回溯:递归中,当某一分支无法满足条件时,我们需要回溯,取消之前的选择,尝试其他分割方式。

实现思路

  • 从字符串的第一个字符开始,逐步检查每一个前缀是否是回文串。
  • 如果是回文串,则将该前缀作为一个可能的子串,并递归处理剩余的字符串。
  • 当字符串被完全分割(即没有剩余字符串时),将该分割方案保存起来。
  • 使用回溯来尝试不同的分割方案。

步骤

  • 判断回文:首先我们需要一个辅助函数来判断某个字符串的某个区间是否为回文串。
  • 递归与回溯:我们需要递归遍历字符串的每个前缀,并尝试将其作为一个回文串。
  • 终止条件:当遍历到字符串的末尾时,说明当前路径已经找到一个可行的分割方案,将其加入结果中。

代码

 public List<List<String>> partition(String s) {
        List<List<String>> res = new ArrayList<List<String>>();
        if(s == null || s.isEmpty())
            return res;
        if(s.length()==1){
            ArrayList<String> strings = new ArrayList<String>();
            strings.add(s);
            res.add(strings);
        }
        List<String> stringList = new ArrayList<>();
        fun(s,stringList,res,0);
        return res;
    }

    private void fun(String s, List<String> stringList, List<List<String>> res, int start) {
        if(start == s.length()){
            List<String> now = new ArrayList<>(stringList);
            res.add(now);
        }
        for(int i=start;i<s.length();i++){
            String str = s.substring(start,i+1);
            if(check(str)){
                stringList.add(str);
                fun(s,stringList,res,i+1);
                stringList.removeLast();
            }
        }
    }


    private boolean check(String s) {
        char[] charArray = s.toCharArray();
        int i=0,j=s.length()-1;
        while(i<j){
            if(charArray[i]!=charArray[j]){
                return false;
            }
            i++;
            j--;
        }
        return true;
    }

    public static void main(String[] args) {
        test0910 test = new test0910();
        System.out.println(test.partition("aabcd"));
    }

回溯——N皇后

题目

51. N 皇后 - 力扣(LeetCode)

思路

  • 基本思想

    • 回溯法:N 皇后问题的本质是一个排列组合问题。通过递归与回溯的方式,可以在棋盘的每一行中放置一个皇后,并检查是否满足约束条件(没有冲突)。一旦发现一个合法的解,就将它加入结果集中。
    • 逐行放置:我们在每一行尝试放置皇后,然后检查它是否与之前放置的皇后冲突。如果不冲突,则继续放置下一行的皇后;如果发生冲突,就回溯到上一个位置,重新选择。
  • 冲突检测

    • :每行只能放一个皇后,因此我们只需要在每一行选择一个位置。
    • :通过一个布尔数组 row[i] 来标记第 i 列是否已经放置过皇后。
    • 主对角线:主对角线上的元素坐标差(x - y)是相等的。我们可以使用一个布尔数组 djx1[x - y + n - 1] 来标记主对角线是否被占用。
    • 副对角线:副对角线上的元素坐标和(x + y)是相等的。我们可以使用另一个布尔数组 djx2[x + y] 来标记副对角线是否被占用。
  • 递归与回溯

    • 在每一行放置一个皇后时,首先判断当前列和对角线是否已经被占用。
    • 如果合法,则放置皇后,并递归处理下一行。
    • 如果不合法或递归失败,则回溯到上一行,尝试其他可能的位置。
    • 一旦某一行的所有位置都尝试过且没有成功,则进行回溯,撤销上一行的皇后放置,继续尝试其他位置。
  • 状态保存

    • 使用一个数组 queen[] 来记录每一行皇后放置的位置。例如,queen[i] = j 表示在第 i 行的第 j 列放置了皇后。
    • 通过 queen[] 数组可以方便地生成最终的棋盘布局。

代码

public List<List<String>> solveNQueens(int n) {
        List<List<String>> res = new ArrayList<>();
       int[] queen = new int[n];
       boolean[] row = new boolean[n];
       boolean[] djx1 = new boolean[2*n-1];
       boolean[] djx2 = new boolean[2*n-1];
       fun3(res,queen,row,djx1,djx2,0,n);
       return res;
    }

    private void fun3(List<List<String>> res,int[] queen, boolean[] row, boolean[] djx1, boolean[] djx2, int x, int n) {
        if(x==n){
            res.add(trans(queen,n));
            return;
        }
        for(int i=0;i<n;i++){
            if(row[i]||djx1[x-i+n-1]||djx2[i+x]){
                continue;
            }

            row[i] = true;
            queen[x]=i;
            djx1[x-i+n-1]=true;
            djx2[i+x]=true;

            fun3(res,queen,row,djx1,djx2,x+1,n);

            row[i]=false;
            djx1[x-i+n-1]=false;
            djx2[i+x]=false;
        }
    }

    private List<String> trans(int[] queen, int n) {
        List<String> board = new ArrayList<>();
        for (int i = 0; i < n; i++) {
            char[] row = new char[n];
            for (int j = 0; j < n; j++) {
                row[j] = '.';  // 初始为空位
            }
            row[queen[i]] = 'Q';  // 将皇后放置在第 i 行的正确列
            board.add(new String(row));  // 将当前行加入到棋盘中
        }
        return board;
    }

二分查找——寻找两个正序数组的中位数

题目

4. 寻找两个正序数组的中位数 - 力扣(LeetCode)

思路

对数组进行合并然后找出中位数

但是这样时间复杂度会来到O(m+n)

优化后的思路

为了找到两个有序数组的中位数,我们不需要合并两个数组。可以通过二分查找来确定两个数组的中位数,利用其有序性高效解决

代码

简单代码

public double findMedianSortedArrays(int[] nums1, int[] nums2) {
        int n = nums1.length+nums2.length;
        int[] nums = new int[n];
        int k=0,m=0;
        for(int i=0;i<n;i++){
            if(k==nums1.length){
                nums[i]=nums2[m];
                m++;
                continue;
            }
            if(m==nums2.length){
                nums[i]=nums1[k];
                k++;
                continue;
            }
            if(k<nums1.length&&m< nums2.length&&nums1[k]<nums2[m]){
                nums[i] = nums1[k];
                k++;
            }else if(k<nums1.length&&m< nums2.length&&nums2[m]<=nums1[k]){
                nums[i] = nums2[m];
                m++;
            }
        }
        double result = 0.0;
        if(n%2==0){
            result = ((double) nums[n/2]+(double) nums[n/2-1])/2;
        }else{
            result = (double) nums[n/2];
        }
        return result;
    }

优化后的代码

public double findMedianSortedArrays(int[] nums1, int[] nums2) {
        // 确保 nums1 是较短的数组
        if (nums1.length > nums2.length) {
            return findMedianSortedArrays(nums2, nums1);
        }

        //计算总的左侧元素个数
        int m = nums1.length;
        int n = nums2.length;
        int totalLeft = (m + n + 1) / 2;

        //二分查找
        int left = 0, right = m;
        while (left < right) {
            int i = (left + right + 1) / 2;
            int j = totalLeft - i;

            if (nums1[i - 1] > nums2[j]) {
                right = i - 1;
            } else {
                left = i;
            }
        }

        int i = left;
        int j = totalLeft - i;

        //分割点处的情况分析
        int nums1LeftMax = (i == 0) ? Integer.MIN_VALUE : nums1[i - 1];
        int nums1RightMin = (i == m) ? Integer.MAX_VALUE : nums1[i];
        int nums2LeftMax = (j == 0) ? Integer.MIN_VALUE : nums2[j - 1];
        int nums2RightMin = (j == n) ? Integer.MAX_VALUE : nums2[j];

        //判断中位数
        if ((m + n) % 2 == 1) {
            return Math.max(nums1LeftMax, nums2LeftMax);
        } else {
            return (Math.max(nums1LeftMax, nums2LeftMax) + Math.min(nums1RightMin, nums2RightMin)) / 2.0;
        }
    }

栈——有效的括号

题目

20. 有效的括号 - 力扣(LeetCode)

思路

经典题目,用栈就好了,遇到左括号就入栈,遇到右括号就出栈。最后栈为空则有效,非空则无效。

代码

 public boolean isValid(String s) {
        if (s == null || s.length() == 0) {
            return true;
        }
        Stack<Character> stack = new Stack<>();
        char[] array = s.toCharArray();
        for (char c : array) {
            if (c == '(' || c == '[' || c == '{') {
                stack.push(c);
            } else if (c == ')' || c == ']' || c == '}') {
                if (stack.isEmpty()) {
                    return false;
                }
                char top = stack.pop();
                if (c == ')' && top != '(')
                    return false;
                if (c == ']' && top != '[')
                    return false;
                if (c == '}' && top != '{')
                    return false;
            }
        }
        return stack.isEmpty();
    }

栈——字符串解码

题目

394. 字符串解码 - 力扣(LeetCode)

思路

使用 栈(Stack) 来解决这个问题

  1. 使用两个栈

    • 一个栈保存数字,用来记录重复次数。
    • 另一个栈保存当前的字符串,用来记录已经解析的部分。
  2. 遍历字符串

    • 当遇到数字时,解析出完整的数字。
    • 当遇到 [ 时,表示要开始处理一个新的编码部分,当前字符串应该入栈等待。
    • 当遇到 ] 时,表示结束了一个编码部分,取出栈顶的数字和字符串,重复并连接当前的部分。
    • 当遇到普通字符时,直接将字符追加到当前的字符串中。
  3. 时间复杂度分析

    • 每个字符都会被遍历一次,且每个字符在栈中进出一次,因此时间复杂度为 O(n),其中 n 是字符串的长度。

代码

public String decodeString(String s) {
        if(s.isEmpty()){
            return s;
        }
        Stack<Integer> integerStack = new Stack<>();
        Stack<StringBuilder> stringStack = new Stack<>();
        char[] chars = s.toCharArray();
        StringBuilder sb = new StringBuilder();
        int k = 0;
        for (char aChar : chars) {
            if (aChar == '[') {
                integerStack.push(k);
                stringStack.push(sb);
                sb = new StringBuilder();
                k = 0;
            } else if (aChar == ']') {
                int temp = integerStack.pop();
                StringBuilder str = stringStack.pop();
                for (int j = 0; j < temp; j++) {
                    str.append(sb);
                }
                sb = str;
            } else if (Character.isDigit(aChar)) {
                k = k * 10 + (aChar - '0');
            } else {
                sb.append(aChar);
            }
        }
        return sb.toString();
    }

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2135825.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

初学者指南:如何在Windows 11中自定义任务栏颜色,全面解析!

Windows任务栏如何修改颜色&#xff1f;任务栏可以说是电脑桌面上比较不“起眼”的东西&#xff0c;但是也有不少小伙伴会想要将自己的电脑任务栏设置得好看&#xff0c;比如说修改电脑任务栏透明度&#xff0c;以及修改任务栏颜色。 电脑任务栏设置可以修改任务栏颜色&#xf…

mysql学习教程,从入门到精通,SQL ORDER BY 子句(14)

1、SQL ORDER BY 子句 在本教程中&#xff0c;您将学习如何对SELECTSQL查询返回的数据进行排序。 1.1、对结果集排序 通常&#xff0c;当您使用SELECT语句从表中获取数据时&#xff0c;结果集中的行没有任何特定的顺序。如果要按特定顺序排列结果集&#xff0c;则可以在语句…

镜舟科技与中启乘数科技达成战略合作,共筑数据服务新生态

当今企业数据管理日益规范化&#xff0c;数据应用系统随着数据类型与数量的增长不断细分&#xff0c;为了提升市场竞争力与技术实力&#xff0c;数据领域软件服务商与上下游伙伴的紧密对接与合作显得尤为重要。通过构建完善的生态系统&#xff0c;生态内企业间能够整合资源、共…

只有C盘的windows系统通过磁盘分区分出D盘

为什么要从C盘中分出D盘&#xff1f; windows电脑的一个良好的操作规范是&#xff1a;C盘是系统盘&#xff0c;D盘是软件盘&#xff0c;E盘是数据盘&#xff0c;软件一般安装在D盘&#xff0c;大家的一些数据资料可以放在E盘&#xff0c;软件大家一般按照在C盘系统盘&#xff…

GD - GD32350R_EVAL - PWM实验和验证3 - EmbeddedBuilder - 无源蜂鸣器 - 用PMOS来控制

文章目录 GD - GD32350R_EVAL - PWM实验和验证3 - EmbeddedBuilder - 无源蜂鸣器 - 用PMOS来控制概述笔记失败图成功图蜂鸣器管脚波形总结END GD - GD32350R_EVAL - PWM实验和验证3 - EmbeddedBuilder - 无源蜂鸣器 - 用PMOS来控制 概述 以前做了一个实验&#xff0c;用PMOS来…

电阻、电容、电感的封装大小分别与什么参数有关?

电阻封装大小与电阻值、额定功率有关&#xff1b; 电容封装大小与电容值、额定电压有关&#xff1b; 电感封装大小与电感量、额定电流有关。

4款高效的视频剪辑工具,帮你记录精彩瞬间。

随着各种主流媒体的流行&#xff0c;视频剪辑对与很多人来说都不是难题。因为相较于那些专业门槛相对较高的剪辑工具&#xff0c;现在有很多的剪辑工具使用起来都很简单&#xff0c;也完全能够满足大部分的剪辑需求。这次&#xff0c;我便要帮大家盘点4款专业、简单、易用的视频…

绕过CDN查找真实IP方法

1、前言 在新型涉网案件中&#xff0c;我们在搜集到目标主站之后常常需要获取对方网站的真实IP去进一步的信息搜集&#xff0c;但是现在网站大多都部署了CDN&#xff0c;将资源部署分发到边缘服务器 实现均衡负载&#xff0c;降低网络堵塞&#xff0c;让用户能够更快地访问自己…

AI智能体:一步步教你制作扣子工作流

这是一篇关于字节智能体平台扣子制作工作流的笔记。 完整智能体可参考&#xff1a;基于扣子(Coze)打造第一个智能体——个性化对话机器人 使用工作流优化机器人输出 1 旅游机器人的业务流程 提到工作流&#xff0c;不要感觉有什么高大上的&#xff0c;工作流本质就是我们完…

根据NVeloDocx Word模板引擎生成Word(六-结束)

前面几篇已经把E6开发平台配套的Word模版隐藏NVeloDocx的基础用法介绍了一遍&#xff0c;这些基础用法基本上可以完全覆盖实际业务的绝大部分需求。所以我们这一篇就介绍一些边边角角的内容&#xff0c;给本系列来一个首尾。 本篇的主要内容有&#xff1a; 1、汇总计算&#…

Nacos1.X中对NacosNamingService的实现

Nacos服务注册与发现的实现原理图 服务注册与发现的功能&#xff1a; 服务实例启动时注册到服务注册表、关闭时则注销&#xff08;服务注册&#xff09;服务注册中心根据服务实例定时发送的心跳包&#xff0c;实现健康检测&#xff08;健康检查BeatReactor中的BeatTask&#x…

打造最佳自闭症患全寄宿学校:为孩子的未来保驾护航

在自闭症儿童教育的广阔领域里&#xff0c;寻找一所能够全方位关注孩子成长、为他们的未来奠定坚实基础的学校&#xff0c;是许多家庭的心愿。广州的星贝育园自闭症儿童寄宿制学校&#xff0c;正是这样一所致力于成为最佳的自闭症儿童全寄宿学校&#xff0c;它以独特的教育理念…

软件测试学习笔记丨Postman基础使用

本文转自测试人社区&#xff0c;原文链接&#xff1a;https://ceshiren.com/t/topic/32096 一、Postman基础使用 1.1 简介 Postman是一款流行的API测试工具和开发环境&#xff0c;旨在简化API开发过程、测试和文档编制。优势&#xff1a; Postman可以快速构建请求&#xff0c…

使用 React Testing Library 测试自定义 React Hooks

自定义 React hooks为开发人员提供了在多个组件之间提取和重用常见功能的能力。然而&#xff0c;测试这些 hooks可能会有些棘手&#xff0c;特别是对于测试新手来说。在本文中&#xff0c;我们将探讨如何使用 React Testing Library 测试自定义 React hook。 测试 React组件 首…

录屏工具大揭秘:录屏快捷键、工具使用感受与建议

在繁忙的工作中&#xff0c;我们常常需要记录下一些重要的操作步骤或精彩瞬间&#xff0c;这时录屏工具就派上了用场&#xff1b;接下来&#xff0c;我将以轻松愉悦的方式&#xff0c;为大家介绍四款常用的录屏工具及其快捷键&#xff0c;并分享使用感受与建议&#xff1a; 录…

OM6626国产低功耗蓝牙对比NRF52832/NRF52810

OM6626 是一款超低功耗的蓝牙soc 主要特性&#xff1a; 支持BLE5.3支持SIG Mesh支持2.4G长包主频64Mhz&#xff0c;80KB RAM主要应用在esl电子价签&#xff0c;IoT模组、CGM、高报告率HID设备 PUM特点 1.71~3.6v供电电压1秒间隔广播平均电流&#xff1a;9uA&#xff1b;1秒间…

架构设计 - 常用日志收集方案选型对比与推荐

目录 1. 常用组合1.1 ELK Stack -> Elastic Stack1.2 EFK Stack1.3 Graylog1.4 PLG 日志系统1.5 Splunk1.6 Filebeat ELK1.7 AWS CloudWatch Logs1.8 阿里云日志服务1.9 腾讯云 CLS&#xff08;日志服务&#xff09; 2. 推荐 日志收集是系统监控和调试中的关键环节。常见的…

心觉:以终为始,帮你精准实现目标

Hi&#xff0c;我是心觉&#xff0c;与你一起玩转潜意识、脑波音乐和吸引力法则&#xff0c;轻松掌控自己的人生&#xff01; 挑战每日一省写作169/1000天 假设你的目标是 一年内赚到150万。我们可以通过“以终为始”和“以始为终”的结合来帮助你实现这个目标 以下是完整的…

VuePress搭建文档网站/个人博客(简单配置、易上手)

天行健&#xff0c;君子以自强不息&#xff1b;地势坤&#xff0c;君子以厚德载物。 每个人都有惰性&#xff0c;但不断学习是好好生活的根本&#xff0c;共勉&#xff01; 文章均为学习整理笔记&#xff0c;分享记录为主&#xff0c;如有错误请指正&#xff0c;共同学习进步。…

sourcetree配置ssh连接gitee

使用PuttyGen.exe生成的公钥私钥格式和git文档方法生成的不一样&#xff0c; SSH 公钥设置 | Gitee 帮助中心 gitee方法生成的公钥类似&#xff1a; ssh-ed25519 AAAA***5B Gitee SSH Key PuttyGen.exe生成的&#xff1a; 公钥 ---- BEGIN SSH2 PUBLIC KEY ---- Comment:…