在这个问题中,我们需要检查子字符串s1是否出现在给定字符串s中子字符串s2的任何出现之后。我们可以比较s1和s2在字符串s中的起始索引来解决这个问题。 p>
问题陈述——我们给出了三个子字符串,名为 s、s1 和 s2。字符串 s 始终包含 s1 作为子字符串。我们需要检查给定字符串 s 中子字符串 s1 是否出现在子字符串 s2 出现之后。
示例输入– s =“abxtutorialspointwelcomepoint”,s1 =“欢迎”,s2 =“点”;
输出 – 是
解释 – 在字符串 s 中,“point”子字符串出现了 2 次。一个在“欢迎”之前,另一个在“欢迎”之后。所以,我们可以说字符串 s1 出现在字符串 s2 的任何出现之后
输入– s = abcdefgh, s1 = abcd, s2 = gh;
输出 – 否
解释s1位于字符串s的开头。因此,s1不会出现在子字符串s2之后。
输入– s =“abce”,s1 =“bc”,s2 =“xy”;
输出 – 否
说明 – 由于字符串 s2 不存在于字符串 s 中,因此打印 no。
方法 1在这种方法中,我们将找到 s2 子字符串的所有起始索引并将它们存储在集合中。之后,我们将得到s1的起始索引。我们将 s2 的每个起始索引与 s1 的起始索引进行比较,如果我们发现集合中的任何值小于 s2 的起始索引,则可以说子字符串 s1 出现在子字符串 s2 的任何出现之后。
算法定义存储子串s2起始索引的集合。
使用 find() 方法查找 s2 子字符串的第一个起始索引。
使用while循环获取子字符串s2的所有起始索引,并使用insert()方法将它们存储到集合中。
遍历设定值。如果任何值小于给定字符串 s 中子字符串 s1 的起始索引,则返回 true。
最后返回 false。
示例#include <iostream>#include <string>#include <unordered_set>using namespace std;bool iss1afters2(string& s, string& s1, string& s2) { // set to store indices of s2 in s unordered_set<int> indices; // find all occurrences of s2 in s, and store them in set size_t found = s.find(s2); while (found != string::npos) { indices.insert(found); found = s.find(s2, found + 1); } // compare starting indices of s1 with s2 for (const int& index : indices) { if (index < s.find(s1)) { return true; // s2 appears before s1 } } return false; // s1 appears before or at the same position as s2}int main(){ string s = abxtutorialspointwelcomepoint; string s1 = welcome, s2 = point; if(iss1afters2(s, s1, s2)) { cout << yes, string s1 appears after string s2.; } else { cout << no, string s1 does not appear after string s2.; } return 0;}
输出yes, string s1 appears after string s2.
时间复杂度 - o(n*k),因为我们需要找到字符串 s2 的起始索引。
空间复杂度 - o(n),因为我们存储字符串 s2 的起始索引。
方法2在这种方法中,我们将遍历字符串。如果我们发现 s2 在 s1 出现之前出现,则返回 true,因为字符串 s 始终包含字符串 s1。
算法定义len、n1和n2变量来存储变量的长度。
开始遍历字符串。
定义‘temp 字符串,并使用从第 i 个索引开始的长度为 n2 的子字符串对其进行初始化。
如果 temp == s2,则返回 true。
从第 i 个索引开始取长度为 n1 的子字符串。如果 temp == s1,则返回 false。
最后返回true。
示例#include <bits/stdc++.h>using namespace std;bool iss1afters2(string &s, string &s1, string &s2){ // store the length of the strings int n1 = s1.size(), n2 = s2.size(); // traverse the string s from left to right for (int i = 0; i <= s.size() - n2; i++){ // temporary string to store substring string temp; // get the substring temp = s.substr(i, n2); // if we find the string s2, return true as s1 always present in s. if (temp == s2){ return true; } temp = s.substr(i, n1); // if we find s1 before s2, return false if (temp == s1){ return false; } } return true;}int main(){ string s = abxtutorialspointwelcome; string s1 = welcome, s2 = point; if(iss1afters2(s, s1, s2)) { cout << yes, string s1 appears after string s2.; } else { cout << no, string s1 does not appear after string s2.; } return 0;}
输出yes, string s1 appears after string s2.
时间复杂度 – o(n*min(n1, n2)),因为我们找到长度为 n1 和 n2 的子字符串。
空间复杂度 - o(min(n1, n2),因为我们存储子字符串。
在第一种方法中,我们使用集合来存储s2的起始索引,这比第二种方法的代码需要更多的空间。第二种方法的代码比第一种方法更具可读性。另外,程序员可以尝试解决检查子串s2是否出现在s1出现之后的问题。
以上就是检查给定句子中,子串s2的任何出现后是否出现子串s1的详细内容。