leetcode
leetcode 2051 ~ 2100
最长的字母序连续子字符串的长度

最长的字母序连续子字符串的长度

难度:

标签:

题目描述

代码结果

运行时间: 124 ms, 内存: 17.0 MB


/*
题目思路:
- 在 Java 中使用流的方式处理问题,首先将字符串转换为字符流,然后通过滑动窗口的方式检查每两个字符是否连续。
- 最后通过收集器计算出最长的连续子字符串长度。
*/

import java.util.stream.IntStream;

public class Solution {
    public int longestContinuousSubstring(String s) {
        return IntStream.range(1, s.length())
                .map(i -> (s.charAt(i) - s.charAt(i - 1) == 1) ? 1 : -i)
                .map(new int[] { 0, 0 }, (a, b) -> {
                    a[1] = b < 0 ? 1 : a[1] + 1;
                    a[0] = Math.max(a[0], a[1]);
                    return a;
                })[0];
    }
}

解释

方法:

该题解采用一次遍历的方式寻找最长的字母序连续子字符串。首先,初始化两个变量来记录当前连续子字符串的长度(`tt`)和最大长度(`m`)。遍历字符串中的每一个字符,通过比较当前字符的ASCII码值与前一个字符的ASCII码值加一是否相等来判断字符是否连续。如果不连续,先比较并可能更新最大长度`m`,然后重置当前连续长度`tt`。最后,遍历结束后再次检查并更新最大长度,以防最长连续子字符串出现在字符串的末尾。

时间复杂度:

O(n)

空间复杂度:

O(1)

代码细节讲解

🦆
为什么这个算法在判断字符是否连续时,使用ASCII码的比较而不是直接比较字符?
在Python中,字符可以直接比较,但是使用ASCII码比较可以更直观地表示字符的顺序关系。通过计算ASCII值并比较它们,我们可以清晰地验证两个字符是否按字母顺序连续。例如,'a'的ASCII是97,'b'是98,直接使用ASCII值比较可以明确地看出它们是否连续。这种方法在逻辑上更清晰,代码也更易于理解和维护。
🦆
在最后一次循环后,为什么需要再次检查并可能更新最大长度`m`?
算法在遍历过程中只有在字符序列断开时才会更新最大长度`m`。如果最长的连续子字符串恰好出现在字符串的末尾,那么在循环结束时这个最长的连续子字符串还没有被检查和更新到`m`中。因此,需要在循环结束后再次检查`tt`(当前连续子字符串的长度),以确保包括末尾的连续子字符串长度在内的最大长度被正确计算和返回。
🦆
如果输入字符串`s`的长度为1,这个算法是否能正确处理并返回长度为1的结果?
是的,该算法能够正确处理长度为1的字符串。根据算法初始化时设置的`tt = 1`,即使字符串只有一个字符,`tt`已经记录了这个单个字符的长度。由于没有更多的字符进行比较,循环不会执行。因此,最终返回的`m`在最后一次检查中会被`tt`更新,正确地返回1。
🦆
在算法中,变量`tt`在遇到不连续的字符时为什么要设置为0,而不是1?这与算法的逻辑是否一致?
这实际上是算法中的一个错误。在遇到不连续的字符时,应该将`tt`重置为1,而不是0。因为每个字符至少可以单独构成一个长度为1的连续子字符串。将`tt`设置为0会导致算法在处理断点后的第一个字符时丢失这个字符的计数。因此,正确的做法应该是在断点后将`tt`重置为1,以确保连续计数的正确性和算法的逻辑一致性。

相关问题