简体   繁体   中英

String within a string recursive function error

I have a problem with a recursive function I'm trying to write. The purpose of the function is to find a string within a string and then return the index at which the second string is located inside the first using recursion.

I am able to do this. The problem comes when the second string isn't contained in the first string. I'm want to out to the user that the second string was not found. I can't get it to relay that message.

int index_of(string s, string t){
  int len1 = s.length(), len2 = t.length(), index = 0;
  if (len1==len2){
     if (s.substr(index, len2) == t){
       return index;
     }else{
       return -1;
     }
  else{
    index++;
    return index_of(s.substr(index, len1),t)+index;
  }
}

int main(){ 
  string strOne = "", strTwo = "";
  cout << "This program will find the ocurrence of one string within        another.\n\nEnter the string to be searched:\t";
  getline(cin, strOne);
  cout << "\nNow enter the string you want to search for:\t";
  getline(cin, strTwo);
  int index = index_of(strOne, strTwo);
  if (index == -1){
    cout << "\nThe second string cannot be found. Sorry!\n\n";}
  else{
    cout << "\nThe index of the substring is:\t" << index << "\n\n";
  }
  system("PAUSE");
  return 0;
}

Any help would be greatly appreciated! :)

If first string doesn't contain the second, index being incremented infinitely making string s zero length. So you have to check, whether the first string is shorter than the second. If so, it doesn't contain the substring.

  if (len1 < len2){
    // first string doesn't contain the second
    return -2;
  }else if (len1==len2){
    ...

But you shouldn't use recursive function here at all. Also there is a built-in function find in string : Check this question: Check if a string contains a string in C++

There are a number of problems in the code you've posted, first and formost, that it won't compile, because you don't define index in index_of . And of course, you only do the comparison whenthe two strings are the same length. But it's hard to figure out what the comparison is that you're trying to do, since you take a substring based on the undefined variable index ; if index is 0 , the there is no point in taking the substring, and if index isn't 0 , then s.substr( index, len2 ) == t can never be true (since you only enter this branch if both s and t have the same length.

What you really have to do is start by defining in plain English what the function should do:

  • If s is shorter than t , no match is possible, so you return -1.

  • Otherwise, if the start of s is equal to t , you return the current index.

  • Otherwise, you recurse on the substring of s , removing the first character (and incrementing index ).

Of course, you also need to maintain index somewhere; in classical recursion, this would be as an additional function argument.

Frankly, I would not construct all of those substrings. It's far more idiomatic in C++ to use iterators. And I would wrap the recursive function in a non-recursive one, so that the user wouldn't have to pass in any extra arguments: the user might call something like:

int
indexOf( std::string const& text, std::string const& target )
{
    return indexOf( 0, text.begin(), text.end(), target );
}

Or, without passing the extra argument:

int
indexOf( std::string const& text, std::string const& target )
{
    std::string::const_iterator results 
            = search( text.begin(), text.end(), target );
    return results == text.end()
        ?  -1
        :  results - text.begin();
}

(I'm assuming that this is homework; one wouldn't normally use recursion for a problem like this. Otherwise, of course, just call std::search in the second version, and the job is done. Or text.find( target ) , which returns almost exactly what you want.)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM