【算法系列篇】滑动窗口
文章目录
- 前言
- 什么是滑动窗口
- 1.长度最小的子数组
- 1.1 题目要求
- 1.2 做题思路
- 1.3 Java代码实现
- 2.无重复字符的最长子串
- 2.1 题目要求
- 2.2 做题思路
- 2.3 Java代码实现
- 3.最大连续1的个数 III
- 3.1 题目要求
- 3.2 做题思路
- 3.3 Java代码实现
- 4.将x减到0的最小操作数
- 4.1 题目要求
- 4.2 做题思路
- 4.3 Java代码实现
- 5.水果成篮
- 5.1 题目要求
- 5.2 做题思路
- 5.3 Java代码实现
- 6.找到字符串中所有字母异位词
- 6.1 题目要求
- 6.2 做题思路
- 6.3 Java代码实现
- 7.串联所有单词的子串
- 7.1 题目要求
- 7.2 做题思路
- 7.3 Java代码实现
- 8.最小覆盖字串
- 8.1 题目要求
- 8.2 做题思路
- 8.3 Java代码实现
- 总结
前言
前面我们学习了什么是双指针,今天我将为大家分享一种特殊的双指针——滑动窗口,为什么说它是特殊的双指针呢?因为它也是有两个指针维护的,并且两个指针的移动方向是相同的,就跟我们平时生活中的窗口一样,两条边是往相同的方向移动的。
什么是滑动窗口
滑动窗口算法是一种用于解决数组或字符串相关问题的算法。它通过两个指针维护的一个窗口,在窗口内进行操作,并根据问题的要求移动窗口的起始位置或结束位置。
滑动窗口算法通常用于解决需要在连续子数组或子字符串中寻找最大值、最小值、满足特定条件的值等问题。它的基本思想是通过调整窗口的大小和位置,以便在不重复计算的情况下,高效地处理问题。
滑动窗口算法的步骤如下:
- 初始化窗口的起始位置和结束位置。
- 根据问题的要求,移动窗口的起始位置或结束位置。
- 在每次移动窗口时,根据窗口内的元素进行相应的操作,例如计算最大值、最小值、满足特定条件的值等。
- 重复步骤2和步骤3,直到窗口移动到数组或字符串的末尾。
滑动窗口算法的时间复杂度通常为O(n),其中n为数组或字符串的长度。它通过避免重复计算,提高了问题的解决效率。
我们通过几个例子来了解滑动窗口算法。
1.长度最小的子数组
https://leetcode.cn/problems/minimum-size-subarray-sum/
1.1 题目要求
给定一个含有 n 个正整数的数组和一个正整数 target 。
找出该数组中满足其和 ≥ target 的长度最小的 连续子数组 [numsl, numsl+1, …, numsr-1, numsr] ,并返回其长度。如果不存在符合条件的子数组,返回 0 。
示例 1:
输入:target = 7, nums = [2,3,1,2,4,3]
输出:2
解释:子数组 [4,3] 是该条件下的长度最小的子数组。
示例 2:
输入:target = 4, nums = [1,4,4]
输出:1
示例 3:
输入:target = 11, nums = [1,1,1,1,1,1,1,1]
输出:0
提示:
1 <= target <= 109
1 <= nums.length <= 105
1 <= nums[i] <= 105
class Solution {public int minSubArrayLen(int target, int[] nums) {}
}
1.2 做题思路
我们先来看看,如果使用暴力解法该怎么做。分别以每个数字开始,向后找 和>=target的子数组。
暴力解法是通过两层循环,i 从 0开始,j 从 i+1 开始遍历整个数字,找到 和 >= target 的长度最小的子数组。并且这个和是每次循环都从 0 开始加的。
通过观察每次循环找到的长度最小的子数组,我们可以发现,left 指针和 right 指针都是向同一个方向向右移动的,暴力解法是每次循环结束之后 right 的位置就回到 left + 1 的位置,这样就多了很多重复的不必要的计算。所以滑动窗口就是在这个暴力解法的基础上进行优化的,每次 right 的指向不进行返回,而是继续向右滑动,那么为什么 right 的指向可以不用返回呢?因为每次循环 left 的指向都会向右移动一位,而你要想找的长度最小的子数组的和 >= target,你的 right 就必须也是向右移动或者不移动,但是绝对不会是向左移动(在数组元素都是正数的情况下),这种就是滑动窗口的基本特征。
那么知道了使用滑动窗口这个算法的时候,我们来看看具体应该如何实现。定义一个 sum 变量,存储每次进窗口之后这个窗口元素的和,并且这个sum 不是每一次都是逐个累加而是用之前的 sum 加上进窗口的这个元素,当 sum >= target 的时候,就需要进行出窗口的操作,并且在出窗口的时候,还需要判断是否需要更新 ret 的值,继续寻找后面的长度最小的子数组,每出一个元素,sum 就需要减去这个出去的数,出窗口一直出到 sum < target,然后再进窗口,反复上面的操作,直到 right 到达数组末尾。
1.3 Java代码实现
class Solution {public int minSubArrayLen(int target, int[] nums) {int ret = Integer.MAX_VALUE;for(int left = 0,right = 0, sum = 0; right < nums.length; right++) {sum += nums[right];while(sum >= target) {ret = Math.min(ret,right - left + 1);sum -= nums[left++];}}return ret == Integer.MAX_VALUE ? 0 : ret;}
}
2.无重复字符的最长子串
https://leetcode.cn/problems/longest-substring-without-repeating-characters/
2.1 题目要求
给定一个字符串 s ,请你找出其中不含有重复字符的 最长子串 的长度。
示例 1:
输入: s = "abcabcbb"
输出: 3
解释: 因为无重复字符的最长子串是 "abc",所以其长度为 3。
示例 2:
输入: s = "bbbbb"
输出: 1
解释: 因为无重复字符的最长子串是 "b",所以其长度为 1。
示例 3:
输入: s = "pwwkew"
输出: 3
解释: 因为无重复字符的最长子串是 "wke",所以其长度为 3。请注意,你的答案必须是 子串 的长度,"pwke" 是一个子序列,不是子串。
提示:
0 <= s.length <= 5 * 104
s 由英文字母、数字、符号和空格组成
class Solution {public int lengthOfLongestSubstring(String s) {}
}
2.2 做题思路
先来看看暴力解法如何解决
通过暴力解法,我们也可以发现,每次循环找到的无重复字符的最长子串它的 left 的 right 都是向右移动的,所以这个题目同样使用滑动窗口来解决。
因为这里求的是长度最长的无重复字符的子串,所以需要在进窗口的时候进行判断是否需要更新最大长度,而判断是否有重复的字符,我们可以借助哈希表来进行判断。
2.3 Java代码实现
class Solution {public int lengthOfLongestSubstring(String ss) {char[] s = ss.toCharArray();int[] hash = new int[128];int ret = 0;for(int left = 0, right = 0; right < s.length; right++) {char in = s[right];hash[in]++;if(hash[in] == 1) {ret = Math.max(ret,right - left + 1);}while(hash[in] > 1) {char out = s[left++];hash[out]--;}}return ret;}
}
3.最大连续1的个数 III
https://leetcode.cn/problems/max-consecutive-ones-iii/
3.1 题目要求
给定一个二进制数组 nums 和一个整数 k,如果可以翻转最多 k 个 0 ,则返回 数组中连续 1 的最大个数 。
示例 1:
输入:nums = [1,1,1,0,0,0,1,1,1,1,0], K = 2
输出:6
解释:[1,1,1,0,0,1,1,1,1,1,1]
粗体数字从 0 翻转到 1,最长的子数组长度为 6。
示例 2:
输入:nums = [0,0,1,1,0,0,1,1,1,0,1,1,0,0,0,1,1,1,1], K = 3
输出:10
解释:[0,0,1,1,1,1,1,1,1,1,1,1,0,0,0,1,1,1,1]
粗体数字从 0 翻转到 1,最长的子数组长度为 10。
提示:
1 <= nums.length <= 105
nums[i] 不是 0 就是 1
0 <= k <= nums.length
class Solution {public int longestOnes(int[] nums, int k) {}
}
3.2 做题思路
很多人看到这个翻转0不知道啥意思,说通俗点就是0可以变成1,同样,先来看看暴力解法如何解决。
left 指针和 right 指针都是向右方向移动的,所以这道题目同样使用滑动窗口来解决。我们的判断条件是以窗口内0的数量为判断条件,并且求的是最大长度,所以是在进窗口的时候进行判断。
3.3 Java代码实现
class Solution {public int longestOnes(int[] nums, int k) {int ret = 0;for(int left = 0, right = 0,count = 0; right < nums.length; right++) {if(nums[right] == 0) count++;if(count <= k) {ret = Math.max(ret,right - left + 1);}while(count > k) {if(nums[left++] == 0) count--;}}return ret;}
}
4.将x减到0的最小操作数
https://leetcode.cn/problems/minimum-operations-to-reduce-x-to-zero/
4.1 题目要求
给你一个整数数组 nums 和一个整数 x 。每一次操作时,你应当移除数组 nums 最左边或最右边的元素,然后从 x 中减去该元素的值。请注意,需要 修改 数组以供接下来的操作使用。
如果可以将 x 恰好 减到 0 ,返回 最小操作数 ;否则,返回 -1 。
示例 1:
输入:nums = [1,1,4,2,3], x = 5
输出:2
解释:最佳解决方案是移除后两个元素,将 x 减到 0 。
示例 2:
输入:nums = [5,6,7,8,9], x = 4
输出:-1
示例 3:
输入:nums = [3,2,20,1,1,3], x = 10
输出:5
解释:最佳解决方案是移除后三个元素和前两个元素(总共 5 次操作),将 x 减到 0 。
提示:
1 <= nums.length <= 105
1 <= nums[i] <= 104
1 <= x <= 109
class Solution {public int minOperations(int[] nums, int x) {}
}
4.2 做题思路
这道题目的意思就是:给定一个数字x,每次从数组的最左边或者最右边选择一个数减去,然后使x减到0的最少的操作数。这道题目如果从正面去做的话,会先的非常麻烦,不妨我们换一条思路,他求的是数组两边减去的最少的数字,不妨我们就求数组中间最长的子数组,使它们的和为数组所有元素的总和减去 target ,这样就能是数组的两侧的和为 target 并且长度最短。所以这个题目就跟前面的求数组长度最长的子数组是差不多的,就只是判断的地方不同,这里需要在出窗口之后判断是否需要更新ret的值,这里我就不给大家过多介绍了,关键就是能够知道这个思路。
4.3 Java代码实现
class Solution {public int minOperations(int[] nums, int x) {int sum = 0;for(int n : nums) sum += n; //求数组所有元素的总和int target = sum - x;if(target < 0) return -1;int ret = -1;for(int left = 0, right = 0,sum1 = 0; right < nums.length; right++) {sum1 += nums[right];while(sum1 > target) {sum1 -= nums[left++];}if(sum1 == target) {ret = Math.max(ret,right - left + 1);}}return ret == -1 ? -1 : nums.length - ret;}
}
5.水果成篮
https://leetcode.cn/problems/fruit-into-baskets/
5.1 题目要求
你正在探访一家农场,农场从左到右种植了一排果树。这些树用一个整数数组 fruits 表示,其中 fruits[i] 是第 i 棵树上的水果 种类 。
你想要尽可能多地收集水果。然而,农场的主人设定了一些严格的规矩,你必须按照要求采摘水果:
- 你只有 两个 篮子,并且每个篮子只能装 单一类型 的水果。每个篮子能够装的水果总量没有限制。
- 你可以选择任意一棵树开始采摘,你必须从 每棵 树(包括开始采摘的树)上 恰好摘一个水果 。采摘的水果应当* 符合篮子中的水果类型。每采摘一次,你将会向右移动到下一棵树,并继续采摘。
- 一旦你走到某棵树前,但水果不符合篮子的水果类型,那么就必须停止采摘。
给你一个整数数组 fruits ,返回你可以收集的水果的 最大 数目。
示例 1:
输入:fruits = [1,2,1]
输出:3
解释:可以采摘全部 3 棵树。
示例 2:
输入:fruits = [0,1,2,2]
输出:3
解释:可以采摘 [1,2,2] 这三棵树。
如果从第一棵树开始采摘,则只能采摘 [0,1] 这两棵树。
示例 3:
输入:fruits = [1,2,3,2,2]
输出:4
解释:可以采摘 [2,3,2,2] 这四棵树。
如果从第一棵树开始采摘,则只能采摘 [1,2] 这两棵树。
示例 4:
输入:fruits = [3,3,3,1,2,1,1,2,3,3,4]
输出:5
解释:可以采摘 [1,2,1,1,2] 这五棵树。
提示:
1 <= fruits.length <= 105
0 <= fruits[i] < fruits.length
class Solution {public int totalFruit(int[] fruits) {}
}
5.2 做题思路
根据题目我们可以知道,只有两个篮子,只能装两种水果,并且每个篮子可以装的水果数是无限的,这道题跟子数组的问题是类似的,只是判断条件变成了水果的种类,进窗口的时候,添加水果的种类很简单,当这个种类的水果数量在之前为0时,就说明是一个新的种类,但是当我们出窗口的时候,如果某一种类的水果数量减为0的时候,就需要减去一种种类,那么我们如何统计某一水果的数量呢?哈希表,使用哈希表可以很高效的对某一种类的数量进行统计。
5.3 Java代码实现
class Solution {public int totalFruit(int[] fruits) {int ret = 1;int[] hash = new int[fruits.length];for(int left = 0, right = 0,kinds = 0; right < fruits.length; right++) {int in = fruits[right];if(hash[in]++ == 0) kinds++;if(kinds <= 2) { //当水果的种类小于等于2的时候就需要做出判断ret = Math.max(ret,right - left + 1);}while(kinds > 2) {int out = fruits[left++];if(--hash[out] == 0) kinds--;}}return ret;}
}
6.找到字符串中所有字母异位词
https://leetcode.cn/problems/find-all-anagrams-in-a-string/
6.1 题目要求
给定两个字符串 s 和 p,找到 s 中所有 p 的 异位词 的子串,返回这些子串的起始索引。不考虑答案输出的顺序。
异位词 指由相同字母重排列形成的字符串(包括相同的字符串)。
示例 1:
输入: s = "cbaebabacd", p = "abc"
输出: [0,6]
解释:
起始索引等于 0 的子串是 "cba", 它是 "abc" 的异位词。
起始索引等于 6 的子串是 "bac", 它是 "abc" 的异位词。
示例 2:
输入: s = "abab", p = "ab"
输出: [0,1,2]
解释:
起始索引等于 0 的子串是 "ab", 它是 "ab" 的异位词。
起始索引等于 1 的子串是 "ba", 它是 "ab" 的异位词。
起始索引等于 2 的子串是 "ab", 它是 "ab" 的异位词。
提示:
1 <= s.length, p.length <= 3 * 104
s 和 p 仅包含小写字母
class Solution {public List<Integer> findAnagrams(String s, String p) {}
}
6.2 做题思路
这道题其实就相当于使用一个大小为 p 字符串长度的框从 s 字符串头部开始框 p 字符串长度的字符串,然后判断框起来的字符串是否是 p 字符串的异位词。
窗口中的大小是确定的,最终的窗口的大小是p字符串的长度,也就是说我们的判断条件就是窗口内的字符串是否是p字符串的异位词,这也是解决这道题的关键。那么我们应该如何解决呢?同样是使用两个哈希表,第一个哈希表统计p字符串每个单词出现的次数,当进窗口的时候,第二个哈希表中该字符出现的次数就加一,并且如果将这个字符添加进哈希表之后,该哈希表中对应字符出现的次数小于等于第一个哈希表对应字符出现的次数,就说明进窗口的这个字符为有效字符,我们使用 count 来记录有效字符的个数,count++,当 count 等于 p 字符串的长度时,就需要更新结果:将 left 的坐标添加进列表中。
6.3 Java代码实现
class Solution {public List<Integer> findAnagrams(String ss, String pp) {List<Integer> list = new ArrayList<>();char[] s = ss.toCharArray();char[] p = pp.toCharArray();int[] hash1 = new int[26];int[] hash2 = new int[26];for(char ch : p) hash1[ch - 'a']++;int len = p.length;for(int left = 0, right = 0,count = 0; right < s.length; right++) {char in = s[right];if(++hash2[in - 'a'] <= hash1[in - 'a']) count++;if(right - left + 1 > len) {char out = s[left++];if(hash2[out - 'a']-- <= hash1[out - 'a']) count--;}if(count == len) {list.add(left);}}return list;}
}
7.串联所有单词的子串
https://leetcode.cn/problems/substring-with-concatenation-of-all-words/
7.1 题目要求
给定一个字符串 s 和一个字符串数组 words。 words 中所有字符串 长度相同。
s 中的 串联子串 是指一个包含 words 中所有字符串以任意顺序排列连接起来的子串。
- 例如,如果 words = [“ab”,“cd”,“ef”], 那么 “abcdef”, “abefcd”,“cdabef”, “cdefab”,“efabcd”, 和 “efcdab” 都是串联子串。 “acdbef” 不是串联子串,因为他不是任何 words 排列的连接。
返回所有串联子串在 s 中的开始索引。你可以以 任意顺序 返回答案。
示例 1:
输入:s = "barfoothefoobarman", words = ["foo","bar"]
输出:[0,9]
解释:因为 words.length == 2 同时 words[i].length == 3,连接的子字符串的长度必须为 6。
子串 "barfoo" 开始位置是 0。它是 words 中以 ["bar","foo"] 顺序排列的连接。
子串 "foobar" 开始位置是 9。它是 words 中以 ["foo","bar"] 顺序排列的连接。
输出顺序无关紧要。返回 [9,0] 也是可以的。
示例 2:
输入:s = "wordgoodgoodgoodbestword", words = ["word","good","best","word"]
输出:[]
解释:因为 words.length == 4 并且 words[i].length == 4,所以串联子串的长度必须为 16。
s 中没有子串长度为 16 并且等于 words 的任何顺序排列的连接。
所以我们返回一个空数组。
示例 3:
输入:s = "barfoofoobarthefoobarman", words = ["bar","foo","the"]
输出:[6,9,12]
解释:因为 words.length == 3 并且 words[i].length == 3,所以串联子串的长度必须为 9。
子串 "foobarthe" 开始位置是 6。它是 words 中以 ["foo","bar","the"] 顺序排列的连接。
子串 "barthefoo" 开始位置是 9。它是 words 中以 ["bar","the","foo"] 顺序排列的连接。
子串 "thefoobar" 开始位置是 12。它是 words 中以 ["the","foo","bar"] 顺序排列的连接。
提示:
1 <= s.length <= 104
1 <= words.length <= 5000
1 <= words[i].length <= 30
words[i] 和 s 由小写英文字母组成
class Solution {public List<Integer> findSubstring(String s, String[] words) {}
}
7.2 做题思路
这道题目跟上面的一个题目是类似的,只是这里将字母换成了单词,所以我们可以仿照上面一个题的思路,将words数组中的每个字符串当作一个字母,s 字符串每与words数组中每个单词相同长度的字符串作为一个字母。
因为不仅可以从 b 开始,将字符数组分为多个字符串,还可以从a和r开始,所以这里我们需要进行 words 数组中每个单词长度的循环次数的操作。
这里的哈希表用数组就不容易模拟了,所以这里就需要用到 HashMap
7.3 Java代码实现
class Solution {public List<Integer> findSubstring(String s, String[] words) {List<Integer> list = new ArrayList<>();Map<String,Integer> map1 = new HashMap<>();for(String tmp : words) {map1.put(tmp,map1.getOrDefault(tmp,0) + 1);}int len = words.length; //求words数组的大小int m = words[0].length(); //求words数组中每个单词的长度for(int i = 0; i < m; i++) {Map<String,Integer> map2 = new HashMap<>();for(int left = i, right = i, count = 0; right <= s.length()-m; right += m) {String in = s.substring(right,right + m);map2.put(in,map2.getOrDefault(in,0) + 1);if(map2.get(in) <= map1.getOrDefault(in,0)) count++;if(right - left + 1 > len * m) {String out = s.substring(left,left + m);if(map2.get(out) <= map1.getOrDefault(out,0)) count--;map2.put(out,map2.get(out) - 1);left += m;}if(count == len) list.add(left);}}return list;}
}
8.最小覆盖字串
https://leetcode.cn/problems/minimum-window-substring/
8.1 题目要求
给你一个字符串 s 、一个字符串 t 。返回 s 中涵盖 t 所有字符的最小子串。如果 s 中不存在涵盖 t 所有字符的子串,则返回空字符串 “” 。
注意:
对于 t 中重复字符,我们寻找的子字符串中该字符数量必须不少于 t 中该字符数量。
如果 s 中存在这样的子串,我们保证它是唯一的答案。
示例 1:
输入:s = "ADOBECODEBANC", t = "ABC"
输出:"BANC"
解释:最小覆盖子串 "BANC" 包含来自字符串 t 的 'A'、'B' 和 'C'。
示例 2:
输入:s = "a", t = "a"
输出:"a"
解释:整个字符串 s 是最小覆盖子串。
示例 3:
输入: s = "a", t = "aa"
输出: ""
解释: t 中两个字符 'a' 均应包含在 s 的子串中,
因此没有符合条件的子字符串,返回空字符串。
提示:
m == s.length
n == t.length
1 <= m, n <= 105
s 和 t 由英文字母组成
class Solution {public String minWindow(String s, String t) {}
}
8.2 做题思路
因为这道题目中说了,可以出现重复的字符,所以这道题的判断条件就是窗口中是否含有 t 字符串中的所有字符,并且窗口中的每个字符出现的次数必须大于 t 字符串中每个字符出现的次数。那么这道题的步骤主要分为两步:
- 在s字符串中,找到含有 t 字符串中含有的所有字符的窗口
- 在这个窗口中找长度最小的子串
8.3 Java代码实现
class Solution {public String minWindow(String ss, String tt) {char[] s = ss.toCharArray();char[] t = tt.toCharArray();int[] hash1 = new int[128];int[] hash2 = new int[128];int kinds = 0;for(char ch : t) {if(hash1[ch]++ == 0) kinds++;}int begin = -1;int minLen = Integer.MAX_VALUE;for(int left = 0, right = 0,count = 0; right < s.length; right++) {char in = s[right];if(++hash2[in] == hash1[in]) count++;while(count == kinds) {if(right - left + 1 < minLen) {begin = left;minLen = right - left + 1;}char out = s[left++];if(hash2[out]-- == hash1[out]) count--;}}if(begin == -1) return new String();else return ss.substring(begin,begin + minLen);}
}
总结
当涉及到解决子串或子数组的问题时,滑动窗口算法是一种非常有效的技术。它通过维护一个窗口,该窗口在字符串或数组上滑动,以解决特定问题。
滑动窗口算法的主要思想是使用两个指针,一个指向窗口的起始位置,另一个指向窗口的结束位置。通过调整这两个指针,可以扩展或收缩窗口,以找到所需的解。算法的关键是确定窗口的移动规则以及如何在移动过程中更新解。
下面是滑动窗口算法的一般步骤:
- 初始化窗口的起始指针和结束指针,使其指向合理的位置。
- 进入一个循环,不断尝试扩展窗口,直到窗口无法再扩展为止。
- 在每次窗口移动时,更新解(如果有必要)。
- 如果窗口仍然满足问题的要求,尝试收缩窗口,以寻找更优的解。
- 重复步骤3和4,直到窗口完全收缩并处理完所有元素。
滑动窗口算法的优点是其时间复杂度通常是线性的,因为它避免了对每个子串或子数组的重复计算,节约了计算资源。它也通常可以在O(1)的空间复杂度下完成。
滑动窗口算法常用于解决一些经典问题,例如字符串匹配、子数组和子串求和、最长/最短子数组等。通过适当定义窗口的移动规则和解的更新方式,可以针对不同的具体问题进行定制化的实现。
总结而言,滑动窗口算法是一种高效的解决子串或子数组问题的方法。它的核心思想是通过维护一个窗口,在问题的限定条件下移动窗口的起始和结束指针,同时利用解的特性来优化计算过程。使用滑动窗口算法可以提高问题的解决效率,并减少不必要的计算。
相关文章:
【算法系列篇】滑动窗口
文章目录 前言什么是滑动窗口1.长度最小的子数组1.1 题目要求1.2 做题思路 1.3 Java代码实现2.无重复字符的最长子串2.1 题目要求2.2 做题思路2.3 Java代码实现 3.最大连续1的个数 III3.1 题目要求3.2 做题思路3.3 Java代码实现 4.将x减到0的最小操作数4.1 题目要求4.2 做题思路…...
多维时序 | MATLAB实现BiTCN-BiGRU-Attention多变量时间序列预测
多维时序 | MATLAB实现SABO-CNN-GRU-Attention多变量时间序列预测 目录 多维时序 | MATLAB实现SABO-CNN-GRU-Attention多变量时间序列预测预测效果基本介绍模型描述程序设计参考资料 预测效果 基本介绍 多维时序 | MATLAB实现BiTCN-BiGRU-Attention多变量时间序列预测。 模型描…...
Docker容器与虚拟化技术:Docker compose部署LNMP
目录 一、理论 1.LNMP架构 2.背景 3.Dockerfile部署LNMP 3.准备Nginx镜像 4.准备MySQL容器 5.准备PHP镜像 6.上传wordpress软件包 7.编写docker-compose.yml 8.构建与运行docker-compose 9.启动 wordpress 服务 10.浏览器访问 11.将运行中的 docker容器保存为 doc…...
高性能服务器Nodejs操作Mysql数据库
目录 1 Node 操作 mysql1.2 操作 mysql 数据库 2 Web 开发模式2.1 服务端渲染2.2 前后端分离2.3 如何选择 3 身份认证3.1 Session 认证机制3.2 JWT 认证机制 1 Node 操作 mysql 数据库和身份认证 配置 mysql 模块 安装 mysql 模块 npm install mysql建立连接 const mysql …...
ffmpeg将rtsp流转成mp4
命令行版本 ffmpeg -y -i "rtsp://你的rtsp地址" -vcodec copy -f mp4 d:/1.mp4中间的rtsp网址一定要加上双引号,避免出现url有特殊字符的问题 java代码版本 如果不支持tcp协议,去掉下面两个参数即可,加上这两个参数是因为ffmpeg默认使用ud…...
第十四天|层序遍历、226.翻转二叉树 (优先掌握递归)、101. 对称二叉树 (优先掌握递归)
层序遍历 题目链接:102. 二叉树的层序遍历 - 力扣(LeetCode) /*** Definition for a binary tree node.* struct TreeNode {* int val;* TreeNode *left;* TreeNode *right;* TreeNode() : val(0), left(nullptr), right(n…...
如何使用装rancher安装k8s集群(k8s集群图形化管理工具)
前言 kubernetes集群的图形化管理工具主要有以下几种: 1、 Kubernetes Dashborad: Kubernetes 官方提供的图形化工具 2、 Rancher: 目前比较主流的企业级kubernetes可视化管理工具 3、各个云厂商Kubernetes集成的管理器 4、 Kuboard: 国产开源Kubernetes可视化管理…...
类加载器与双亲委派
类加载器与双亲委派 Java 类加载器(Class Loader)是 Java 虚拟机(JVM)的一部分,负责将类的字节码加载到内存中,并将其转换为可执行的 Java 对象。类加载器在 Java 应用程序中起着重要的作用,它…...
用Python创造乐趣:编写你自己的探索游戏世界
在当今数字化时代,编程不再是一个专业程序员的专利。无论你是一个编程新手还是有一定经验的开发者,用Python编写简单的游戏是一个有趣且富有创造性的方式。在这篇博客中,我们将探索如何用Python构建一个基本的探索游戏世界,让玩家…...
git stash弹出栈中的指定内容
使用 git stash 的相关命令来选择性地弹出特定的 stash 内容,应用到指定的分支上。如果我们使用 git stash 命令已经存储了多个记录时,每个 stash 记录都会有一个唯一的标识符(stash{0}、stash{1}…)。通过这些标识符可以应用或弹…...
5.7 汇编语言:汇编高效乘法运算
乘法指令是一种在CPU中实现的基本算术操作,用于计算两个数的乘积。在汇编语言中,乘法指令通常是通过mul(无符号乘法)和imul(有符号乘法)这两个指令实现的。由于乘法指令在执行时所消耗的时钟周期较多&#…...
Graphql中的N+1问题
开篇 原文出处 Graphql 是一种 API 查询语言和运行时环境,可以帮助开发人员快速构建可伸缩的 API。然而,尽管 Graphql 可以提供一些优秀的查询性能和数据获取的能力,但是在使用 Graphql 的过程中,开发人员也会遇到一些常见问题&…...
mysql、oracle、sqlserver常见方法区分
整理了包括字符串与日期互转、字符串与数字互转、多行合并为一行、拼接字段等一些常用的函数,当然有些功能实现的方法不止一种,这里列举了部分常用的,后续会持续补充。 MySQLOracleSQL Server字符串转数字 CAST(123 as SIGNED) 或 CONVERT(12…...
AcWing 4382. 快速打字
原题链接:AcWing 4382. 快速打字 关键词:双指针、判断子序列 芭芭拉是一个速度打字员。 为了检查她的打字速度,她进行了一个速度测试。 测试内容是给定她一个字符串 I,她需要将字符串正确打出。 但是,芭芭拉作为一…...
DataFrame.query()--Pandas
1. 函数功能 Pandas 中的一个函数,用于在 DataFrame 中执行查询操作。这个方法会返回一个新的 DataFrame,其中包含符合查询条件的数据行。请注意,query 方法只能用于筛选行,而不能用于筛选列。 2. 函数语法 DataFrame.query(ex…...
【C语言】美元名字和面额对应问题
题目 美元硬币从小到大分为1美分(penny)5美分(nickel)10美分(dime)25美分(quarter)和50美分(half-dollar),写一个程序实现当给出一个数字面额可以…...
uniapp隐藏底部导航栏(非自定义底部导航栏)
uniapp隐藏底部导航栏 看什么看,要多看uni官方文档,里面啥都有 看什么看,要多看uni官方文档,里面啥都有 uniapp官方网址:uni设置TabBar // 展示 uni.showTabBar({animation:true,success() {console.debug(隐藏成功)…...
CSS background 背景
background属性为元素添加背景效果。 它是以下属性的简写,按顺序为: background-colorbackground-imagebackground-repeatbackground-attachmentbackground-position 以下所有示例中的花花.jpg图片的大小是4848。 1 background-color background-col…...
安防监控视频平台EasyCVR视频汇聚平台和税务可视化综合管理应用方案
一、方案概述 为了确保税务执法的规范性和高效性,国家税务总局要求全面推行税务系统的行政执法公示制度、执法全过程记录制度和重大执法决定法制审核制度。为此,需要全面推行执法全过程记录制度,并推进信息化建设,实现执法全过程的…...
深度学习实战50-构建ChatOCR项目:基于大语言模型的OCR识别问答系统实战
大家好,我是微学AI,今天给大家介绍一下深度学习实战50-构建ChatOCR项目:基于大语言模型的OCR识别问答系统实战,该项目是一个基于深度学习和大语言模型的OCR识别问答系统的实战项目。该项目旨在利用深度学习技术和先进的大语言模型,构建一个能够识别图像中文本,并能够回答与…...
计算机安全学习笔记(I):访问控制安全原理
访问控制原理 从广义上来讲,所有的计算机安全都与访问控制有关。 RFC 4949: Internet Security Glossary, Version 2 (rfc-editor.org) RFC 4949 定义的计算机安全:用来实现和保证计算机系统的安全服务的措施,特别是保证访问控制服务的措施…...
Linux 虚拟机安装 hadoop
目录 1 hadoop下载 2 解压hadoop 3 为 hadoop 文件夹改名 4 给 hadoop 文件夹赋权 5 修改环境变量 6 刷新环境变量 7 在hadoop313目录下创建文件夹data 8 检查文件 9 编辑 ./core-site.xml文件 10 编辑./hadoop-env.sh文件 11 编辑./hdfs-site.xml文件 12 编辑./mapr…...
FxFactory 8 Pro Mac 苹果电脑版 fcpx/ae/motion视觉特效软件包
FxFactory pro for mac是应用在Mac上的fcpx/ae/pr视觉特效插件包,包含了成百上千的视觉效果,打包了很多插件,如调色插件,转场插件,视觉插件,特效插件,文字插件,音频插件,…...
解决问题:如何在 Git 中查看提交历史
可以使用以下命令查看 Git 中的提交历史: git log这将显示当前分支上的所有提交历史。每个提交的输出包括提交哈希(SHA-1 值)、作者、日期和提交注释。 您也可以添加一些选项,以获取更详细的提交历史: --oneline 显示…...
不同规模的测试团队分别适合哪些测试用例管理工具?测试用例管理工具选型指南
随着软件系统规模的持续增大,业务复杂度的持续增加,软件测试的复杂度也随之越来越大。软件测试工作的复杂性主要体现在测试用例的编写、维护、执行和管理方面。而创建易于阅读、维护和管理的测试用例能够显著减轻测试工作的复杂性。 本篇文章将较为系统的…...
服务器遭受攻击,CPU升高,流量升高,你一般如何处理
服务器遭受攻击,CPU升高,流量升高,你一般如何处理? 在什么情况下服务器遭受攻击,会导致CPU升高,流量升高 1.DDoS(分布式拒绝服务攻击):这是一种常见的网络攻击方式&…...
GPT生产实践之定制化翻译
GPT生产实践之定制化翻译 GPT除了能用来聊天以外,其实功能非常强大,但是我们如何把它运用到生产实践中去,为公司带来价值呢?下面一个使用案例–使用gpt做专业领域定制化翻译 思路: 定制化:有些公司词条的…...
SpringMVC入门笔记
一、SpringMVC简介 1. 什么是MVC MVC是一种软件架构的思想,将软件按照模型、视图、控制器来划分 M:Model,模型层,指工程中的JavaBean,作用是处理数据 JavaBean分为两类: 一类称为实体类Bean࿱…...
如何构建多域名HTTPS代理服务器转发
在当今互联网时代,安全可靠的网络访问是至关重要的。本文将介绍如何使用SNI Routing技术来构建多域名HTTPS代理服务器转发,轻松实现多域名的安全访问和数据传输。 SNI代表"Server Name Indication",是TLS协议的扩展,用于…...
【Java 高阶】一文精通 Spring MVC - 数据验证(七)
👉博主介绍: 博主从事应用安全和大数据领域,有8年研发经验,5年面试官经验,Java技术专家,WEB架构师,阿里云专家博主,华为云云享专家,51CTO 专家博主 ⛪️ 个人社区&#x…...
wordpress 简约博客/长沙市云网站建设
前言 Java虚拟机有自己完善的硬件架构,如处理器、堆栈等,还具有相应的指令系统。 Java虚拟机本质上就是一个程序,当它在命令行上启动的时候,就开始执行保存在某字节码文件中的指令。Java语言的可移植性正是建立在Java虚拟机的基础…...
制作网站支付方式/营销策略有哪些内容
现在国内的 Java 主力版本仍是 Java 8,所以对于「Java 8 是否要收费」这个问题,十分有必要阐述清楚,以消除不必要的恐慌。首先要明确一点,Java 仍然是免费的,并不需要付费使用!下面解释「Java 8 要收费」这…...
商城展示网站/希爱力吃一颗能干多久
背景 先前开源了一个开源项目: 【阿里巴巴开源项目: 基于mysql数据库binlog的增量订阅&消费】 本文主要是介绍一下如何部署&使用 环境要求 1. 操作系统 a. 纯java开发,windows/linux均可支持 b. jdk建议使用1.6.25以上的版本,稳定…...
免费网站制作手机软件的app/seo运营推广
文章目录写在前面投光物平行光点光源衰减选择正确的值实现衰减聚光手电筒平滑/软化边缘总结练习写在前面 原文链接。原文应该是github上的一个项目,本文主要用来记录一些知识点和自己遇到的问题。 投光物 我们目前使用的光照都来自于空间中的一个点。它能给我们不…...
信用卡网站建设/网络热词
文章目录 前言I 添加新的实例变量1.1 原理1.2 关联对象的行为1.3 例子II 动态创建属性2.1 应用场景2.2 例子:为VC新增一个属性2.3 效果III 删除属性See Also前言 添加新的实例变量的原理:利用category结合runtime的对象关联(associated objects)实现 应用: 添加私有属性用…...
做海报设计的网站/新网站快速收录
常用oracle的函数使用说明一,字符操作类:1,字符串的连接concat或者||update o_test aset a.column1 concat (a.column1,a. column2)把column1和column2两个字段的值加在一起赋给了column1update o_test aset a.column1 a.column1||a. colum…...