Searching for a Substring Appearing Multiple Times

How do I handle searching for a substring within a string when the substring can appear multiple times?

To handle searching for a substring that appears multiple times within a string, you can use a loop with the std::string::find() function. This method allows you to locate all occurrences of the substring.

Using a Loop with std::string::find()

Here's an example:

#include <iostream>
#include <string>

int main() {
  std::string text = "This is a test."
    "This test is only a test.";
  std::string target = "test";
  std::size_t pos = text.find(target);

  while (pos != std::string::npos) {
    std::cout << "Found '" << target
      << "' at position " << pos << "\n";
    pos = text.find(target, pos + target.length());  
  }
}
Found 'test' at position 10
Found 'test' at position 20
Found 'test' at position 35

Explanation

  • std::string::find() searches for the first occurrence of the substring.
  • The loop continues searching by updating the position to start just after the last found substring.
  • The loop terminates when std::string::npos (indicating no more occurrences) is returned.

Handling Overlapping Substrings

If the substrings can overlap, adjust the position increment. By incrementing the position by 1, overlapping occurrences are also found:

#include <iostream>
#include <string>

int main() {
  std::string text = "aaa";
  std::string target = "aa";
  std::size_t pos = text.find(target);

  while (pos != std::string::npos) {
    std::cout << "Found '" << target
      << "' at position " << pos << "\n";
    pos = text.find(target, pos + 1);  
  }
}
Found 'aa' at position 0
Found 'aa' at position 1

Using Regular Expressions

For more complex search patterns, consider using std::regex:

#include <iostream>
#include <regex>
#include <string>

int main() {
  std::string text = "test1 test2 test1 test2";
  std::regex pattern("test[0-9]");

  auto words_begin = std::sregex_iterator(
    text.begin(), text.end(), pattern);
  auto words_end = std::sregex_iterator();

  for (auto it = words_begin; it != words_end; ++it) {
    std::smatch match = *it;
    std::cout << "Found '" << match.str()
      << "' at position "
      << match.position() << "\n";
  }
}
Found 'test1' at position 0
Found 'test2' at position 6
Found 'test1' at position 12
Found 'test2' at position 18

Explanation

  • std::regex allows for complex pattern matching.
  • std::sregex_iterator is used to iterate through all matches.

By using these methods, you can effectively search for a substring that appears multiple times within a string, handling both non-overlapping and overlapping cases, as well as more complex patterns.

Search Algorithms

An introduction to the 8 main searching algorithms in the C++ standard library, including find(), find_if(), find_if_not(), find_first_of(), adjacent_find(), search_n(), search(), and find_end().

Questions & Answers

Answers are generated by AI models and may not have been reviewed. Be mindful when running any code on your device.

Using std::ranges::find() with Custom Data Types
How can I use std::ranges::find() with custom data types that don't implement the equality operator ==?
Case-Insensitive Search Using std::ranges::find_if()
How can I make std::ranges::find_if() case-insensitive when searching through a container of strings?
Finding the Last Occurrence of an Element in a Container
How do I search for the last occurrence of an element using std::ranges::find() or std::find()?
Searching for Multiple Occurrences of a Value in a Container
What is the best way to search for multiple occurrences of a value in a container using standard library algorithms?
Boyer-Moore vs Boyer-Moore-Horspool Search Algorithms
What are the differences and benefits of using std::boyer_moore_searcher versus std::boyer_moore_horspool_searcher in practical scenarios?
Or Ask your Own Question
Get an immediate answer to your specific question using our AI assistant