954,499 Members — Technology Publication meets Social Media
Username:
Password:
Lost login information?
Have something to say? Contribute New Article Reply to this Article

search for string in text file then find a different string after

Hello everyone,
I really need some help with this project I am working on. So I need to go through a text file to search for a particular string (say something like 'play') and then if that word exists in a line I need to find a string after that (say maybe 'try') and copy some numbers after that. I can do the rest but I am having problems searching for the initial string. The sstring 'try' exists in every line and I only want numbers following the string 'try' if the word 'play' also exists in that line. Here is what I have so far

string str_text;

const char searchT[] = "play";
size_t sizeT = strlen (searchT);

const char search[] = "try";
size_t size = strlen (search);
size_t pos = 0;

vector Q;

while ( getline(infile, str_text).good () )
{

if( (pos = str_text.find (searchT, 0)) != string::npos ) //Find 'play'.
{
str_text = str_text.erase (pos, sizeT) ;
}

if ( (pos = str_text.find (search, 0)) != string::npos ) //Find 'try'.
{
str_text = str_text.erase (pos, size) ;

istringstream ins(str_text);
ins >> q;

Q.push_back(q);
}
}


My biggest problem is I just get the numbers after try every time. I dont want the numbers after try if the word play does not exist in the line.

sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 

I forgot to mention that if play exists in the line it is always before the string try.

sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 

Hello everyone, I really need some help with this project I am working on. So I need to go through a text file to search for a particular string (say something like 'play') and then if that word exists in a line I need to find a string after that (say maybe 'try') and copy some numbers after that. I can do the rest but I am having problems searching for the initial string. The sstring 'try' exists in every line and I only want numbers following the string 'try' if the word 'play' also exists in that line. Here is what I have so far

string str_text;

const char searchT[] = "play"; size_t sizeT = strlen (searchT);

const char search[] = "try"; size_t size = strlen (search); size_t pos = 0;

vector Q; while ( getline(infile, str_text).good () ) {

if( (pos = str_text.find (searchT, 0)) != string::npos ) //Find 'play'. { str_text = str_text.erase (pos, sizeT) ; }

if ( (pos = str_text.find (search, 0)) != string::npos ) //Find 'try'. { str_text = str_text.erase (pos, size) ;

istringstream ins(str_text); ins >> q;

Q.push_back(q); } }

My biggest problem is I just get the numbers after try every time. I dont want the numbers after try if the word play does not exist in the line.


We can't run it because it refers to code that isn't listed and we don't have the input file. However, I am guessing that the problem is that you have two if statements, one after the other, and you probably want a NESTED if-statement. You have this (not nested):

if (/* code to find play */)
{
    // code
}

if (/* code to find try */)
{
    // code
}


I'm guessing you want this instead (nested):

if (/* code to find play */)
{
    // code
    if (/* code to find try */)
    {
        // code
    }
}
VernonDozier
Posting Expert
5,527 posts since Jan 2008
Reputation Points: 2,633
Solved Threads: 711
 

I actually thought it should be a nested if - statement like you just mentioned but I get a Debug Assertion failed message with vector subscript out of range. I don't know why that is happening..

This is what I tried,

[/code]
[code = c++]

while ( getline(infile, str_text).good () )
{

if( (posT = str_text.find (searchT, 0)) != string::npos ) //Find 'play'.
{
str_text = str_text.erase (posT ,sizeT) ;

if ( (pos = str_text.find (search, posT)) != string::npos ) //Find try
{
str_text = str_text.erase (pos, size) ;

istringstream ins(str_text);
double q;
ins >> q;

Q.push_back(q);
}
}
}

[/code]

sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 

Post the whole program and the input file so we can run it please.

Regarding code tags, there are no spaces:


[code=cplusplus] <-- no spaces in between brackets
// code
[/code] <-- no spaces in between brackets

VernonDozier
Posting Expert
5,527 posts since Jan 2008
Reputation Points: 2,633
Solved Threads: 711
 

Here is my entire code

[/code]

#include <iostream>
#include <fstream>
#include <sstream>
#include <string>
#include <vector>

using namespace std;

int main () 
{
	// Input and output files.
	string filename;
	
	string inputfilename;  
	cout << " Enter filename (input is filename.txt, output is filename.out): ";
	getline( cin, filename );
	inputfilename = filename + ".txt";
	ifstream infile (inputfilename.c_str());

	string outfilename;
	outfilename = filename + ".out";
	ofstream outfile (outfilename.c_str());

	string str_text;

	const char searchT[] = "play";												
	size_t sizeT = strlen (searchT);
	size_t posT = 0;

	const char search[] = "try";
	size_t size = strlen (search);
	size_t pos = 0;

	vector<double> Q;
	
	while ( getline(infile, str_text).good () )
    {

		if( (pos = str_text.find (searchT, 0)) != string::npos )				//Find 'play'.
		{
			str_text = str_text.erase (pos ,sizeT) ;

			if ( (pos = str_text.find (search, pos)) != string::npos )			//Find try.
			{
				str_text = str_text.erase (pos, size) ;

				istringstream ins(str_text);
				double q;
				ins >> q ;

				Q.push_back(q);
			}
			
			else return 0;
		}
	}

	for (int i=0; i <= Q.size() - 1; i++)
		outfile << Q[i] << "\n";

	
	outfile.close();
	infile.close();

	return 0;
}


I added the else return 0; to get rid of the assertion error but nothing prints in the output file. However if I do the folowing loop in the middle instead i do get the desired number i want but it is for the entire data instead of the lines with just play in it.[/code]

while ( getline(infile, str_text).good () )
    {
 
		if( (pos = str_text.find (searchT, 0)) != string::npos )				//Find 'play'.
		{
			str_text = str_text.erase (pos ,sizeT) ;
                          }
 
			if ( (pos = str_text.find (search, pos)) != string::npos )			//Find try.
			{
				str_text = str_text.erase (pos, size) ;
 
				istringstream ins(str_text);
				double q;
				ins >> q ;
 
				Q.push_back(q);
			}
 

	}
Attachments inputfile.txt (48.07KB)
sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 

I used the code before you edited it. That's a pretty long input file. What should the program do with an input file like this?

hi buy play 5 3 2 try 7 8 9
VernonDozier
Posting Expert
5,527 posts since Jan 2008
Reputation Points: 2,633
Solved Threads: 711
 

well there are two situations
1) ......random hi buy 5 3 2 try 7...... random hi and
2)....... random hi buy play 5 3 2 try 6 8 9 ........ random hi

I want the number right after try i.e 6 in this case (basically case (2)) when there is 'play' before the 'try' before the next random comes along... in situation (1) there is no 'play' so I don't want the number 7 after the 'try'.

I hope that helps and thank you very much for looking into this as I have spent the whole day to no avail so finally decided to get some help.

sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 

well there are two situations 1) ......random hi buy 5 3 2 try 7...... random hi and 2)....... random hi buy play 5 3 2 try 6 8 9 ........ random hi

I want the number right after try i.e 6 in this case (basically case (2)) when there is 'play' before the 'try' before the next random comes along... in situation (1) there is no 'play' so I don't want the number 7 after the 'try'.

I hope that helps and thank you very much for looking into this as I have spent the whole day to no avail so finally decided to get some help.

Okay, for the input file I provided, what should str_text contain AFTER line 46 below is executed?

str_text = str_text.erase (pos, size) ;


given the input line:

hi buy play 5 3 2 try 7 8 9
VernonDozier
Posting Expert
5,527 posts since Jan 2008
Reputation Points: 2,633
Solved Threads: 711
 

I was hoping it would just contain '7 8 9 ........' after line 46 is run.

sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 
I was hoping it would just contain '7 8 9 ........' after line 46 is run.

I'm guessing that you need to change your two erase lines on lines 42 and 46 to the following:

str_text = str_text.erase (0 , pos + sizeT) ; // line 42
str_text = str_text.erase (0 , pos + size) ; // line 46


Add a cout line after line 46 to make sure you get " 7 8 9".

VernonDozier
Posting Expert
5,527 posts since Jan 2008
Reputation Points: 2,633
Solved Threads: 711
 

I solved the problem thanks a lot helping me out...

sammyk
Newbie Poster
7 posts since Apr 2009
Reputation Points: 10
Solved Threads: 0
 

This question has already been solved

Post: Markdown Syntax: Formatting Help
You