Friday, August 1, 2008

C++ explode() function.





Please see efnx's modified version in comments, it is way more efficient than the original. (it does not use temporary vector, and copy it to store - instead it modifies the store vector straight away - which is way more efficient && elegant)





As I have somewhere sometimes stated, I have been writing some php as a hobby. The evidence is CWF Freeware. There's some really handy php functions out there for string manipulation. And since I once needed this, and because I've heard many other's have needed this too, I'll share it with you my readers. (Yes, with both of you :D)

Just a compulsory disclaimer before representing it:

This is one of the functions which I did when I was still a beginner with STL. So there's propably hundred's of more efficient and elegant solutions, and those may be posted in comments here. I'll be glad to see them. But since I happened to find this function from my archives now, I'll give it now. It may be buggy, it may be flawed, but it sure is better than having no explode() in C++ at all. (And yes, standard libraries do not offer explode function in C or C++).


/* This one 'explodes' a string (cuts it into pieces based on some matchstring) and puts pieces into a vector. arguments are the string to be cutted, matchstring and the vector where to store pieces. It returns amount of pieces, and if no matchstring is found it returns -1. */


#include <iostream>
#include <vector>
#include <string>

using std::string;
using std::vector;


int explode(string tear_me,string cut,vector &store)
{
unsigned int start=0;
int len=0;
int i=0;
vector<string> temp;

len=cut.length();
if(tear_me.find(cut)==string::npos)
{
return -1;
}
while( (start=tear_me.find(cut))!=string::npos)
{
temp.push_back(tear_me.substr(0,start));
tear_me.erase(0,start+len);
i++;
}
temp.push_back(tear_me);
store=temp;
return i;
}

5 comments:

  1. I just noticed that < and > characters did their tricks with the displaying the code. Sorry folks. I replaced those with correct html entities, and now the code should be shown completely and correctly.

    -Maz

    ReplyDelete
  2. If you are familiar with the php api
    c++ explode function[zedwood.com] provides the same arguments and return as the php explode function.

    If you wanted to make yours more efficient, you would call store.clear(); first, then call push_back() directly on store, instead of the temp one.

    ReplyDelete
  3. Thanks! I changed your function a little according to what marker said and to fit my naming schemes.

    // explode the string into words, each in an index of a vector
    int explode(std::string line,std::string delimiter,std::vector<std::string> &store)
    {
    unsigned int start = 0;
    int len = 0;
    int i = 0;
    std::vector<std::string> temp;

    store.clear();
    len = delimiter.length();
    if( line.find(delimiter) == std::string::npos ) // if no instance of delimiter exist, exit with -1
    {
    return -1;
    }

    while( (start = line.find(delimiter)) != std::string::npos ) // move along finding delimiter, inc start
    {
    store.push_back( line.substr( 0, start) );
    line.erase( 0, start+len );
    i++;
    }
    return i;
    }

    ReplyDelete
  4. Thank's efnx, it indeed is more efficient to modify the store vector straight away, instead of making a temporary vector and copying it to store. Good work!

    ReplyDelete
  5. Thanks yaa... this was really helpful...

    ReplyDelete