132 找到字符串的最长无重复字符子串
Table of Contents

ac

对应到Leetcode: 面试题48. 最长不含重复字符的子字符串

给定一个数组arr,返回arr的最长无的重复子串的长度(无重复指的是所有字母都不相同)

时间复杂度: O(n)
空间复杂度: O(无重复的数目)

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.*;


public class Main {
    public static Scanner sc = new Scanner(System.in);

    public static BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));

    public static long mod = (long)Math.pow(2,29);

    public static void main(String[] args) throws Exception {
       int n = sc.nextInt();
       int[] arr = new int[n];
       for(int i=0;i<n;i++){
           arr[i] = sc.nextInt();
       }
       System.out.println(getCnt(arr, n));
    }

    static int getCnt(int[] arr, int n){
        int key;
        int value;
        // pre 表示必须在以str[i-1]字符结尾的情况下,最长无重复子串开始位置的前一个位置
        // pre+1 表示在必须在以str[i-1]字符结尾的情况下,最长无重复字符子串的开始位置
        int pre = -1; // 初始为-1
        int len = 0; // 记录最长无重复子串的长度

        // map(str[i])表示之前的遍历中最近一次出现str[i]的位置
        // 假设a位置,想要求以str[i]结尾的最长无重复子串,a位置显然不能包含进来
        // pre 在 a的左边,str[a+1 ... i-1] 都不是重复子串
        Map<Integer,Integer> map = new HashMap<>();
        int cur;
        for(int i=0;i<n;i++){
            if(map.containsKey(arr[i])) {
                pre = Math.max(pre, map.get(arr[i]));
            }
            cur = i - pre; // i - pre 为以i位置结尾的最长无重复子串的长度
            len = Math.max(len, cur);
            map.put(arr[i], i);
        }
        return len;
    }

}
/*
4
2 3 4 5

4

5
2 2 3 4 3

3
*/