跳至主要內容

392. 判断子序列


392. 判断子序列open in new window

🟢   🔖  双指针 字符串 动态规划  🔗 力扣open in new window LeetCodeopen in new window

题目

Given two strings s and t, return true ifs _is a subsequence of _t , orfalse otherwise.

A subsequence of a string is a new string that is formed from the original string by deleting some (can be none) of the characters without disturbing the relative positions of the remaining characters. (i.e., "ace" is a subsequence of " _a_ b _c_ d _e_ " while "aec" is not).

Example 1:

Input: s = "abc", t = "ahbgdc"

Output: true

Example 2:

Input: s = "axc", t = "ahbgdc"

Output: false

Constraints:

  • 0 <= s.length <= 100
  • 0 <= t.length <= 10^4
  • s and t consist only of lowercase English letters.

Follow up: Suppose there are lots of incoming s, say s1, s2, ..., sk where k >= 109, and you want to check one by one to see if t has its subsequence. In this scenario, how would you change your code?

题目大意

给定字符串 st ,判断 s 是否为 t 的子序列。字符串的一个子序列是原始字符串删除一些(也可以不删除)字符而不改变剩余字符相对位置形成的新字符串。(例如,"ace""abcde"的一个子序列,而"aec"不是)。

进阶 :如果有大量输入的 S,称作 S1, S2, ... , Sk 其中 k >= 10亿,你需要依次检查它们是否为 T 的子序列。在这种情况下,你会怎样改变代码?

解题思路

思路一:双指针

使用两个指针 ij 分别指向字符串 st,然后对两个字符串进行遍历,时间复杂度 O(n)

  • 遇到 s[i] == t[j] 的情况,则 i 向右移。
  • 不断右移 j
  • 如果超过 st 的长度则跳出。
  • 最后判断指针 i 是否指向了 s 的末尾,即:判断 i 是否等于 s 的长度。如果等于,则说明 st 的子序列,如果不等于,则不是。

进阶:二分思路

二分思路主要是对 t 进行预处理,用一个字典将每个字符出现的索引位置按顺序存储下来,比如 "abacb" 的字典为:{a: [0, 1], b: [1, 4], c: [3]} ,这样我们不需要每次都遍历 t ,只需查看字典中,是否有满足要求的索引即可。

代码

双指针
/**
 * @param {string} s
 * @param {string} t
 * @return {boolean}
 */
var isSubsequence = function (s, t) {
	let i = 0;
	let j = 0;
	while (i < s.length && j < t.length) {
		if (s[i] == t[j]) {
			i++;
		}
		j++;
	}
	return i == s.length;
};

相关题目

题号标题题解标签难度
792匹配子序列的单词数open in new window字典树 数组 哈希表 4+
1055形成字符串的最短路径 🔒open in new window贪心 双指针 字符串 1+
2486追加字符以获得子序列open in new window贪心 双指针 字符串
2825循环增长使字符串子序列等于另一个字符串open in new window双指针 字符串