[力扣]无重复字符的最长子串

本文介绍了如何解决无重复字符的最长子串问题,通过将字符串转为字符数组,使用哈希映射跟踪字符出现的位置,利用滑动窗口策略处理重复字符,时间复杂度为O(n)。详细解释了解题步骤和一个Java代码示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Problem: 3. 无重复字符的最长子串

思路

此题没有思路. 是看题解做的.
很多时候,看完题后没有任何思路,因为我没有见过类似题型.
所以先思考,没有思路就看题解. 埋头硬想只会失去战斗力.

把题解中的变量命名规范一下,更容易理解.

解题方法

  1. 字符串转换成字符数组.
  2. 定义一个 hashMap, 值作为key, 下标作为value.
  3. 初始化最大总长度 maxCount = 0, 左指针下标为0.
  4. 遍历数组,下标记为rigthIndex,
  5. 如果当前值在 map中存在, 说明出现重复字符了. 需要把左指针移动到重复字符的右边.
  6. 将当前值及当前下标添加到map中.
  7. 计数并和最大长度MaxCount对比,并赋值.

难点

第5步为什么要用leftIndex=Math.max(leftIndex,map.get(rightValue)+1);
而不是直接用leftIndex=map.get(rightValue)+1;

答:在滑动窗口中,左指针只能往右走,不准往后退.
举个容易理解的例子: str=“abba”;
如果不加Math.max, 当右指针下标为3时, 左指针为0. 此时 下标1和下标2重复. 导致错误结果maxCount为3.
如果加了Math.max, 前几轮已经排除了重复数值’b’和’b’.左下标移动到了2, 使用max,保证了下标不会倒回去.

语言表达能力有限,如果理解不了,建议debugger一下就明白了

复杂度

时间复杂度:

应该是O(n)吧

空间复杂度:

算不来

Code

class Solution {
    public int lengthOfLongestSubstring(String str) {
        //1 转成数组
        char[] array = str.toCharArray();
        //2 创建map保存字符.
        HashMap<Character, Integer> map = new HashMap<>();
        //3 定义左指针下标
        int leftIndex = 0;
        //3 定义不重复字符串的长度
        int maxCount = 0;
        //4遍历数组(使用右指针)
        for (int rigthIndex = 0; rigthIndex < array.length; rigthIndex++) {
            //获取右指针对应的值
            char rightValue = array[rigthIndex];
           //如果当前值(右指针指向) 已经在map中存在了.
            if (map.containsKey(rightValue)){
                //5左指针指向map中重复的值.
                //注意: 此时应该注意的,左指针只能往右走, 不能倒着走. 所以使用Math.max判断,是不是倒着走了.    比如 abba 当右指针指向 下标为3的'a'时, 从map中可以查询到下标0的'a', 此时如果将下标移动到 1 那么后边刚刚bb重复,相当于白做了.
                leftIndex=Math.max(leftIndex,map.get(rightValue)+1) ;
            }
            //6将右指针的值和下标放进map中
            map.put(rightValue,rigthIndex);
            //7替换最大值. 
            maxCount = Math.max(maxCount,rigthIndex-leftIndex+1);
        }
        return maxCount;
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值