给你一个整数数组 nums 和一个整数 k 。请你从 nums 中满足下述条件的全部子数组中找出最大子数组和:
子数组的长度是 k,且
子数组中的所有元素 各不相同 。
返回满足题面要求的最大子数组和。如果不存在子数组满足这些条件,返回 0 。
子数组 是数组中一段连续非空的元素序列。
示例 1:
输入:nums = [1,5,4,2,9,9,9], k = 3
输出:15
解释:nums 中长度为 3 的子数组是:
- [1,5,4] 满足全部条件,和为 10 。
- [5,4,2] 满足全部条件,和为 11 。
- [4,2,9] 满足全部条件,和为 15 。
- [2,9,9] 不满足全部条件,因为元素 9 出现重复。
- [9,9,9] 不满足全部条件,因为元素 9 出现重复。
因为 15 是满足全部条件的所有子数组中的最大子数组和,所以返回 15 。
示例 2:
输入:nums = [4,4,4], k = 3
输出:0
解释:nums 中长度为 3 的子数组是:
- [4,4,4] 不满足全部条件,因为元素 4 出现重复。
因为不存在满足全部条件的子数组,所以返回 0 。
提示:
1 <= k <= nums.length <= 105
1 <= nums[i] <= 105
class Solution {
public long maximumSubarraySum(int[] nums, int k) {
//初始化数组和是第一个数
//初始化最大数组和是0
long sum = nums[0];
long max = 0;
int l = 0;
int r = 1;
int n = nums.length;
Map<Integer,Integer> map = new HashMap<>();
for(int num : nums){
map.put(num,0);
}
//初始化第一个数出现的次数是1
map.put(nums[0],1);
while(r<n){
if(map.get(nums[r]) == 0 ){
map.put(nums[r],1);
sum += nums[r];
r++;
if(r-l == k){
max = Math.max(max,sum);
//l++必须把nums[l]出现的次数置0
//sum -= nums[l]
sum -= nums[l];
map.put(nums[l],0);
l++;
}
}else{
//l++必须把nums[l]出现的次数置0
//sum -= nums[l]
map.put(nums[l],0);
sum -= nums[l];
l++;
}
}
//如果k == 1,排序找最大值也是猥琐至极,不会取k == 1的情况了
Arrays.sort(nums);
return k == 1 ? nums[n-1] : max;
}
}
剑指 Offer II 016. 不含重复字符的最长子字符串_模板题目
给定一个字符串 s ,请你找出其中不含有重复字符的 最长连续子字符串 的长度。
示例 1:
输入: s = "abcabcbb"
输出: 3
解释: 因为无重复字符的最长子字符串是 "abc",所以其长度为 3。
示例 2:
输入: s = "bbbbb"
输出: 1
解释: 因为无重复字符的最长子字符串是 "b",所以其长度为 1。
示例 3:
输入: s = "pwwkew"
输出: 3
解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。
请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。
示例 4:
输入: s = ""
输出: 0
提示:
0 <= s.length <= 5 * 104
s 由英文字母、数字、符号和空格组成
注意:本题与主站 3 题相同: https://leetcode-cn.com/problems/longest-substring-without-repeating-characters/
class Solution {
public int lengthOfLongestSubstring(String s) {
int max = 1;
int n = s.length();
if(n == 0) return 0;
int l = 0;
int r = 1;
Map<Character,Integer> map = new HashMap<>();
for(char c : s.toCharArray()){
map.put(c,0);
}
map.put(s.charAt(0),1);
//799. 最长连续不重复子序列模板
while(r < n){
char c = s.charAt(r);
if(map.get(c) == 0){
map.put(c,1);
r++;
max = Math.max(max,r-l);
}else{
char cL = s.charAt(l);
map.put(cL,0);
l++;
}
}
return max;
}
}
最后附上AcWing上求最长连续不重复子串的模板,它真的是一个练习板子很好的网站
799. 最长连续不重复子序列
给定一个长度为 nn 的整数序列,请找出最长的不包含重复的数的连续区间,输出它的长度。
输入格式
第一行包含整数 nn。
第二行包含 nn 个整数(均在 0∼1050∼105 范围内),表示整数序列。
输出格式
共一行,包含一个整数,表示最长的不包含重复的数的连续区间的长度。
数据范围
1≤n≤1051≤n≤105
输入样例:
5
1 2 2 3 5
输出样例:
3
import java.util.*;
import java.math.*;
class Main{
//哈哈哈哈,自己用哈希表写出来了
static int N = 100010;
static int[] a = new int[N];
public static void main(String[] args){
Scanner scanner = new Scanner(System.in);
int n = scanner.nextInt();
Map<Integer,Integer> map = new HashMap<>();
for(int i = 1;i<=n;i++){
a[i] = scanner.nextInt();
}
for(int i = 1;i<=n;i++){
map.put(a[i],0);
}
int l = 1;
int r = 2;
int max = 1;
map.put(a[l],1);
while(r<=n){
if(map.get(a[r]) == 0){
map.put(a[r],1);
r++;
max = Math.max(max,r-l);
}else{
map.put(a[l],0);
l++;
}
}
System.out.print(max);
}
}
码字不易,来自一名非科班的转码生。如果你也喜欢刷算法题的话,一键三连走一波。