题目
392. Is Subsequence
Given a string s and a string t, check if s is subsequence of t.
A subsequence of a string is a new string which is formed from the original string by deleting some (can be none) of the characters without disturbing the relative positions of the remaining characters. (ie, “ace” is a subsequence of “abcde” while “aec” is not).
Follow up:
If there are lots of incoming S, say S1, S2, … , Sk where k >= 1B, and you want to check one by one to see if T has its subsequence. In this scenario, how would you change your code?
Credits:
Special thanks to @pbrother for adding this problem and creating all test cases.
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
- Both strings consists only of lowercase characters.
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/is-subsequence
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
解法一
解决思路:笔者看这道题是二分查找的类型题,很自然就从二分查找,用左右两个坐标同时来匹配。短字符串s的左坐标为sleft, 右坐标为sright; 长字符串t的左坐标为tleft, 右坐标为tright.
检查边界问题,比如短字符为空s == null || s.length() == 0, 则直接返回true;如果长字符为空t == null || t.length() == 0,则直接返回false;
循环遍历条件为长字符串tleft <= tright , 在循环结束前tleft++; tright–;。
如果短字符串的左边字符等于长字符串的左边字符串,则sleft++;;如果短字符串的右边字符等于长字符串的右边字符串,则sright–;。
在结束前判断短字符串的sleft > sright,则返回true。 注意:笔者这里踩过坑,如果放到最前面判断,有可能,长字符串也结束了,导致结果还是false。
public boolean isSubsequence(String s, String t) {
// check edge for s
if (s == null || s.length() == 0) {
return true;
}
// check edge for t
if (t == null || t.length() == 0) {
return false;
}
boolean result = false;
int sleft = 0;
int sright = s.length() - 1;
int tleft = 0;
int tright = t.length() - 1;
while (tleft <= tright) {
if (s.charAt(sleft) == t.charAt(tleft)) {
sleft++;
}
if (s.charAt(sright) == t.charAt(tright)) {
sright--;
}
if (sleft > sright) {
return true;
}
tleft++;
tright--;
}
return result;
}
解法二
笔者跑完以后,以为速度会是最快了,看了以后只能超过87%的提交。看了一下评论,发现还有更优解。
解题思路如下:
遍历短字符串的所有字符,比如遍历到短字符的c,如果长字符集能从前一个找到的字符的位置加一(第一个字符的初始值为-1),能找到当前字符c,则返回第一次找到该字符的位置,则替换index为上一个找到的字符集;如果没有找到当前字符c,则结果是-1,如果是-1,则直接返回false。时间复杂度只有最短字符的长度,最快的情况下,如果第一个字符都没找到就直接退出。神来之笔。
public boolean isSubsequenceByIndexOfChar(String s, String t) {
int index = -1;
for (char c: s.toCharArray()) {
index = t.indexOf(c, index + 1);
if (index == -1) {
return false;
}
}
return true;
}