Mohammad Ali Rony
Mohammad Ali Rony

Reputation: 4905

How to replace n occurrence of a substring in a string in dart?

I want to replace n occurrence of a substring in a string.

myString = "I have a mobile. I have a cat.";

How I can replace the second have of myString

Upvotes: 2

Views: 1160

Answers (5)

BambinoUA
BambinoUA

Reputation: 7100

Here it is one more variant which allows to replace any occurrence in subject string.

void main() {
  const subject = 'I have a dog. I have a cat. I have a bird.';
  final result = replaceStringByOccurrence(subject, 'have', '*have no*', 0);
  print(result);
}

/// Looks for `occurrence` of `search` in `subject` and replace it with `replace`.
///
/// The occurrence index is started from 0.
String replaceStringByOccurrence(
    String subject, String search, String replace, int occurence) {
  if (occurence.isNegative) {
    throw ArgumentError.value(occurence, 'occurrence', 'Cannot be negative');
  }
  final regex = RegExp(r'have');
  final matches = regex.allMatches(subject);
  if (occurence >= matches.length) {
    throw IndexError(occurence, matches, 'occurrence',
        'Cannot be more than count of matches');
  }
  int index = -1;
  return subject.replaceAllMapped(regex, (match) {
    index += 1;
    return index == occurence ? replace : match.group(0)!;
  });
}

Tested on dartpad.

Upvotes: 1

Jahidul Islam
Jahidul Islam

Reputation: 12565

let's try with this

void main() {
  var myString = "I have a mobile. I have a cat.I have a cat";
  print(replaceInNthOccurrence(myString, "have", "test", 1));
}

String replaceInNthOccurrence(
    String stringToChange, String searchingWord, String replacingWord, int n) {
  if(n==1){
    return stringToChange.replaceFirst(searchingWord, replacingWord);
  }
  final String separator = "#######";
  
  String splittingString =
      stringToChange.replaceAll(searchingWord, separator + searchingWord);
  var splitArray = splittingString.split(separator);
  print(splitArray);
  String result = "";
  for (int i = 0; i < splitArray.length; i++) {
    if (i % n == 0) {
      splitArray[i] = splitArray[i].replaceAll(searchingWord, replacingWord);
    }
    result += splitArray[i];
  }
  return result;
}

here the regex

void main() {
  var myString = "I have a mobile. I have a cat. I have a cat. I have a cat.";
   final newString =
      myString.replaceAllMapped(new RegExp(r'^(.*?(have.*?){3})have'), (match) {
    return '${match.group(1)}';
  });
  
  print(newString.replaceAll("  "," had "));
}

Demo link

Upvotes: 1

A K
A K

Reputation: 86

This would be a better solution to undertake as it check the fallbacks also. Let me list down all the scenarios:

  1. If position is 0 then it will replace all occurrence.
  2. If position is correct then it will replace at same location.
  3. If position is wrong then it will send back input string.
  4. If substring does not exist in input then it will send back input string.

void main() {
          String input = "I have a mobile. I have a cat.";
          print(replacenth(input, 'have', 'need', 1));
        }
        
        /// Computes the nth string replace.
        String replacenth(String input, String substr, String replstr,int position) {
          
          if(input.contains(substr))
          {
            var splittedStr = input.split(substr);
            if(splittedStr.length == 0)
              return input;
              
            String finalStr = "";
            
            for(int i = 0; i < splittedStr.length; i++)
            {
              finalStr += splittedStr[i];
              if(i == (position - 1))
                finalStr += replstr;
              else if(i < (splittedStr.length - 1))
                finalStr += substr;
            }
            
            return finalStr;
          }
          
          return input;
        }

Upvotes: 2

rosh-dev851
rosh-dev851

Reputation: 564

hope this simple function helps. You can also extract the function contents if you don't wish a function. It's just two lines with some Dart magic

void main() {
  String myString = 'I have a mobile. I have a cat.';
  String searchFor='have';
  int replaceOn = 2;
  String replaceText = 'newhave';
  String result = customReplace(myString,searchFor,replaceOn,replaceText);
  print(result);
}

String customReplace(String text,String searchText, int replaceOn, String replaceText){
  Match result = searchText.allMatches(text).elementAt(replaceOn - 1);
  return text.replaceRange(result.start,result.end,replaceText);
}

Upvotes: 2

ChessMax
ChessMax

Reputation: 2265

Something like that should work:

String replaceNthOccurrence(String input, int n, String from, String to) {
  var index = -1;
  
  while (--n >= 0) {
    index = input.indexOf(from, ++index);
    if (index == -1) {
      break;
    }
  }
  
  if (index != -1) {
    var result = input.replaceFirst(from, to, index);
    return result;
  }
  
  return input;
} 

void main() {
   var myString = "I have a mobile. I have a cat.";
   var replacedString = replaceNthOccurrence(myString, 2, "have", "had");
   print(replacedString); // prints "I have a mobile. I had a cat."
}

Upvotes: 1

Related Questions