Himanshu
Himanshu

Reputation: 35

Working of erase keyword in string in stl?

I wrote this code to remove consonants from string but my answer is not correct. So what change should i make in this code to make it work correctly. Further more when i remove the space character i.e. last element from unordered set then the output was unexpected to me. So please help me understanding what is going on in this code??

#include<bits/stdc++.h>
using namespace std;

int main() {
   unordered_set<char> a={'a','e','i','o','O','u','U','A','E','I',' '};

   string s="what are you doing";

   string ::iterator it;
   for(it=s.begin();it!=s.end();it++){
      if(a.find(*it)==a.end()){
         s.erase(it);}
    }   

    cout<<s;
    return 0;
}

Upvotes: 0

Views: 79

Answers (1)

Slava
Slava

Reputation: 44238

Your code has issue, when you remove symbol

s.erase(it);

and later increase it by loop you skip a symbol and also may go over the end of string. Possible solution to fix your code:

for(it=s.begin();it!=s.end();){
   if(a.find(*it)==a.end())
      it = s.erase(it);
   else
      ++it;
 }

Note1: usually in STL containers when erasing element by iterator invalidate that iterator. Though documentation for std::string::erase() does not say that any iterator invalidated and possibly it is not the case here. Anyway code I provided will work in any case and with any container and solves your issue as well.

But better to use erase-remove idiom using std::remove_if():

   s.erase( std::remove_if( s.begin(), s.end(), [a] ( char c ){ return a.count(c) == 0; } ), s.end() );

Note2: it is not a good idea to include "bits/stdc++.h"

live example

Upvotes: 2

Related Questions