Related Articles

# Wrap every continuous instance of given word with some given string

• Last Updated : 11 Jun, 2021

Given two string S1 and S2. The task is to wrap every instance of string S2 in string S1 with some string on either side.
Note: Here we will use underscore(_) for the wrapping part. It can be anything as per need, for example some HTML tag, white space, etc.
Examples:

Input: S1 = “examwill be a examexam”, S2 = “exam”
Output: “_exam_will be a _examexam_”
Explanation:
String S2 is “exam“, so wrap occurrence of S2 with underscore. Since, last two occurrence overlaps(in string examexam), so merge both the occurrence and wrap by putting underscore to farther left and farther right of merged substring.
Input: str = “abcabcabcabc”, substr = “abc”
Output: “_abcabcabcabc_”

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.  To complete your preparation from learning a language to DS Algo and many more,  please refer Complete Interview Preparation Course.

In case you wish to attend live classes with experts, please refer DSA Live Classes for Working Professionals and Competitive Programming Live for Students.

Approach: The idea is to simply get the location of all instances of string S2 in S1 and add underscore at either end of the occurrence and if two or more instances of S2 overlaps then, add underscore at either end of the merged substring. Below are the steps:

1. Get the location of all instances of the string S2 in the main string S1. For that traverse string S1 one character at a time and call substring-matching function, find().
2. Create a 2D array of locations(say arr[][]), where each subarray holds the starting and ending indices of a specific instance of the string S2 in the string S1.
3. Merge the overlapping starting and ending index intervals stored in arr[][].
4. After the above steps all the overlapping indexes are merged. Now traverse the given string and intervals at the same time and create a new string by wrapping underscores.
5. Print the new string after the above step.

Below is the implementation of the above approach:

## C++

 `// C++ program for the above approach``#include ``using` `namespace` `std;` `// Function Definations``vector > getLocations(string str,``                                  ``string subStr);` `vector > collapse(``    ``vector > locations);` `string underscorify(string str,``                    ``vector > locations);` `// Function that creates the string by``// wrapping the underscore``string underscorifySubstring(string str,``                             ``string subStr)``{` `    ``// Function Call to intervals of``    ``// starting and ending index``    ``vector > locations``        ``= collapse(getLocations(str, subStr));` `    ``// Function Call``    ``return` `underscorify(str, locations);``}` `// Function finds all starting and ending``// index of the substring in given string``vector > getLocations(string str,``                                  ``string subStr)``{``    ``vector > locations{};``    ``int` `startIdx = 0;` `    ``int` `L = subStr.length();` `    ``// Traverse string str``    ``while` `(startIdx < str.length()) {` `        ``// Find substr``        ``int` `nextIdx = str.find(subStr,``                               ``startIdx);` `        ``// If location found, then insert``        ``// pair int location[]``        ``if` `(nextIdx != string::npos) {` `            ``locations.push_back({ nextIdx,``                                  ``(nextIdx + L) });` `            ``// Update the start index``            ``startIdx = nextIdx + 1;``        ``}``        ``else` `{``            ``break``;``        ``}``    ``}``    ``return` `locations;``}` `// Function to merge the locations``// of substrings that overlap each``// other or sit next to each other``vector > collapse(``    ``vector > locations)``{``    ``if` `(locations.empty()) {``        ``return` `locations;``    ``}` `    ``// 2D vector to store the merged``    ``// location of substrings``    ``vector > newLocations{ locations };` `    ``vector<``int``>* previous = &newLocations;` `    ``for` `(``int` `i = 1; i < locations.size(); i++) {` `        ``vector<``int``>* current = &locations[i];` `        ``// Condition to check if the``        ``// substring overlaps``        ``if` `(current->at(0) <= previous->at(1)) {``            ``previous->at(1) = current->at(1);``        ``}``        ``else` `{``            ``newLocations.push_back(*current);``            ``previous``                ``= &newLocations[newLocations.size() - 1];``        ``}``    ``}``    ``return` `newLocations;``}` `// Function creates a new string with``// underscores added at correct positions``string underscorify(string str,``                    ``vector > locations)``{``    ``int` `locationsIdx = 0;``    ``int` `stringIdx = 0;``    ``bool` `inBetweenUnderscores = ``false``;``    ``vector finalChars{};``    ``int` `i = 0;` `    ``// Traverse the string and check``    ``// in locations[] to append _``    ``while` `(stringIdx < str.length()``           ``&& locationsIdx < locations.size()) {` `        ``if` `(stringIdx``            ``== locations[locationsIdx][i]) {` `            ``// Insert underscore``            ``finalChars.push_back(``"_"``);``            ``inBetweenUnderscores``                ``= !inBetweenUnderscores;` `            ``// Increment location index``            ``if` `(!inBetweenUnderscores) {``                ``locationsIdx++;``            ``}``            ``i = i == 1 ? 0 : 1;``        ``}` `        ``// Create string s``        ``string s(1, str[stringIdx]);` `        ``// Push the created string``        ``finalChars.push_back(s);``        ``stringIdx++;``    ``}` `    ``if` `(locationsIdx < locations.size()) {``        ``finalChars.push_back(``"_"``);``    ``}``    ``else` `if` `(stringIdx < str.length()) {``        ``finalChars.push_back(str.substr(stringIdx));``    ``}` `    ``// Return the resultant string``    ``return` `accumulate(finalChars.begin(),``                      ``finalChars.end(), string());``}` `// Driver Code``int` `main()``{``    ``// Given string S1 and S2``    ``string S1 = ``"examwill be a examexam"``;``    ``string S2 = ``"exam"``;` `    ``// Function Call``    ``cout << underscorifySubstring(S1, S2);``    ``return` `0;``}`

## Java

 `// Java program for the above approach``import` `java.io.*;``import` `java.util.*;` `class` `GFG``{``  ` `    ``// Function that creates the string by``    ``// wrapping the underscore``    ``static` `String underscorifySubstring(String str,``                                        ``String subStr)``    ``{` `        ``// Function Call to intervals of``        ``// starting and ending index``        ``List > locations``            ``= collapse(getLocations(str, subStr));` `        ``// Function Call``        ``return` `underscorify(str, locations);``    ``}` `    ``// Function finds all starting and ending``    ``// index of the substring in given string``    ``static` `List > getLocations(String str,``                                             ``String subStr)``    ``{``        ``@SuppressWarnings``(``"unchecked"``)``        ``List > locations = ``new` `ArrayList();``        ``int` `startIdx = ``0``;` `        ``int` `L = subStr.length();` `        ``// Traverse string str``        ``while` `(startIdx < str.length())``        ``{` `            ``// Find substr``            ``int` `nextIdx = str.indexOf(subStr, startIdx);` `            ``// If location found, then insert``            ``// pair int location[]``            ``if` `(nextIdx != -``1``)``            ``{` `                ``locations.add(Arrays.asList(``new` `Integer[] {``                    ``nextIdx, nextIdx + L }));` `                ``// Update the start index``                ``startIdx = nextIdx + ``1``;``            ``}``            ``else``            ``{``                ``break``;``            ``}``        ``}``        ``return` `locations;``    ``}` `    ``// Function to merge the locations``    ``// of substrings that overlap each``    ``// other or sit next to each other``    ``static` `List >``    ``collapse(List > locations)``    ``{``        ``if` `(locations.size() == ``0``)``        ``{``            ``return` `locations;``        ``}` `        ``// 2D vector to store the merged``        ``// location of substrings``        ``@SuppressWarnings``(``"unchecked"``)``        ``List > newLocations = ``new` `ArrayList();``        ``newLocations.add(locations.get(``0``));` `        ``List previous = locations.get(``0``);` `        ``for` `(``int` `i = ``1``; i < locations.size(); i++)``        ``{` `            ``List current = locations.get(i);` `            ``// Condition to check if the``            ``// substring overlaps``            ``if` `(current.get(``0``) <= previous.get(``1``))``            ``{``                ``previous.set(``1``, current.get(``1``));``            ``}``            ``else``            ``{``                ``newLocations.add(current);``                ``previous = newLocations.get(``                    ``newLocations.size() - ``1``);``            ``}``        ``}``        ``return` `newLocations;``    ``}` `    ``// Function creates a new string with``    ``// underscores added at correct positions``    ``static` `String``    ``underscorify(String str, List > locations)``    ``{``        ``int` `locationsIdx = ``0``;``        ``int` `stringIdx = ``0``;``        ``boolean` `inBetweenUnderscores = ``false``;``        ``StringBuilder finalChars = ``new` `StringBuilder();``        ``int` `i = ``0``;` `        ``// Traverse the string and check``        ``// in locations[] to append _``        ``while` `(stringIdx < str.length()``               ``&& locationsIdx < locations.size()) {` `            ``if` `(stringIdx``                ``== locations.get(locationsIdx).get(i)) {` `                ``// Insert underscore``                ``finalChars.append(``"_"``);``                ``inBetweenUnderscores``                    ``= !inBetweenUnderscores;` `                ``// Increment location index``                ``if` `(!inBetweenUnderscores)``                ``{``                    ``locationsIdx++;``                ``}``                ``i = i == ``1` `? ``0` `: ``1``;``            ``}` `            ``// Push the string``            ``finalChars.append(str.charAt(stringIdx));``            ``stringIdx++;``        ``}` `        ``if` `(locationsIdx < locations.size()) {``            ``finalChars.append(``"_"``);``        ``}``        ``else` `if` `(stringIdx < str.length()) {``            ``finalChars.append(str.substring(stringIdx));``        ``}` `        ``// Return the resultant string``        ``return` `finalChars.toString();``    ``}` `    ``public` `static` `void` `main(String[] args)``    ``{``        ``// Given string S1 and S2``        ``String S1 = ``"examwill be a examexam"``;``        ``String S2 = ``"exam"``;` `        ``// Function Call``        ``System.out.print(underscorifySubstring(S1, S2));``    ``}``}` `// This code is contributed by jithin`
Output:
`_exam_will be a _examexam_`

Time Complexity: O(N * M), where N and M is the length of the string S1 and S2 respectively.
Auxiliary Space: O(N), where N is the length of string S1

My Personal Notes arrow_drop_up