Display a line from text file

Pages: 123
udpated it, but theres error, help please

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
string LReader::getLogs (const string & c, const string & d){

	 ifstream logFile(path.c_str());


	 if (logFile.fail())
	 	    {
	 	        cout << "Can't open file" << endl;
	 	        void exit ();
	 	    }
	 string line2;

	  while (getline (logFile,line2) )
	  {
		  if (line2.find(c) <= line2 && line2 <= line2.find(d)){
			  cout << line2 << endl;

		  }

	  }
}
Now you attempt to:
size_t <= std::string

Did you read http://www.cplusplus.com/reference/string/string/operators/
tried using operators but i still get errors,
where will i put size_t <= std:: string ?
where will i put size_t <= std:: string?
Keskiverto mentioned that you attempted to make that comparison not that you should. Also you wouldn't every compare data types you would compare the variables.

As for where you are doing this is line 15. if (line2.find(c) <= line2 && line2 <= line2.find(d)){ The find method returns a std::size_t http://www.cplusplus.com/reference/string/string/find/
Updated my codes to this, What's wrong? please help me


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
string LReader::getLogs (const string & c, const string & d){

	 ifstream logFile(path.c_str());


	 if (logFile.fail())
	 	    {
	 	        cout << "Can't open file" << endl;
	 	        void exit ();
	 	    }
	 string line2;

	 while (getline (logFile,line2) )
    {
		 std::size_t f1 = line2.find(c);
		 std::size_t f2 =line2.find(d);

		 if (f1 <= line2 && line2 <= f2)
		 lines.push_back(line2);
    }


	 for (size_t i =0; i<lines.size(); i++)
		 cout <<lines [i] << endl;
/*
	 for (int i = 0; i < 10; i++)
	 {
		 getline (logFile, line2);
		 return line2;

	 }*/
return line2;
}
As mentioned earlier if (f1 <= line2 && line2 <= f2) is invalid and I honestly am not sure what you are trying to accomplish with this.
updated it again:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
string LReader::getLogs (const string & c, const string & d){

	 ifstream logFile(path.c_str());


	 if (logFile.fail())
	 	    {
	 	        cout << "Can't open file" << endl;
	 	        void exit ();
	 	    }
	 string line2;

	 while (getline (logFile,line2) )
    {
		 std::size_t f1 = line2.find(c);
		 std::size_t f2 =line2.find(d);

		 if (f1!=std::string::npos )
			 f1++;
		 while {
			 
			 (f2!=std::string::npos) 
			
		 }
			 
		std::cout << line2 << endl;


    }


my problem is in the while function where in I should stop f1++ until it reaches f2
Ugh I don't even know what you are trying to accomplish anymore.

Also what is this supposed to do?
1
2
3
4
5
		 while {
			 
			 (f2!=std::string::npos) 
			
		 }
it shouldn't even compile and even if it did it would be an endless loop.
Update: ALMOST Close to my desired output but: it only shows 9lines it should be 10 lines and there is SEGMENTATION FAULT CORE DUMP?? sorry for my last post , i posted the wrong code. But here's my code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
string LReader::getLogs (const string & c, const string & d){

	 ifstream logFile(path.c_str());


	 if (logFile.fail())
	 	    {
	 	        cout << "Can't open file" << endl;
	 	        void exit ();
	 	    }
	 string line2;

	 while (getline (logFile,line2) )
    {
		 std::size_t f1 = line2.find(c);
		 std::size_t f2 =line2.find(d);

		 if (f1!=std::string::npos )
			 f1++;


		 if (f2!=std::string::npos)

			break;

		std::cout << line2 << endl;


    }


Here's my output:

2014-08-01 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-03 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-04 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-05 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-06 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-07 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-08 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-09 06:13:14,Name,4.5,CustomUnit,CustomType
Segmentation fault (core dumped)


Last edited on
Would you show compilable code please?

Also,
1
2
3
4
5
	 if (logFile.fail())
	 	    {
	 	        cout << "Can't open file" << endl;
	 	        void exit ();
	 	    }
you could do if(logFile) //http://www.cplusplus.com/reference/ios/ios/operator_bool/ Also you might as well just return after it fails.

Oh and if you had some "readable" variable names it would be easier too.. I have no idea what c, d, f1, and f2 are supposed to be.
Last edited on

I'm trying to get the lines from "2014-08-01" to "2014-08-10"
c= "2014-08-01"
d="2014-08-10"

BUT my output only shows from "2014-08-01" to "2014-08-09"
this is my whole program:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
//main


#include <iostream>
#include <string>
#include <fstream>
#include <dirent.h>
#include "LReader.h"

int main(int argc, char* argv[]) {

	LReader l("/home/kaertech/stats_20140801_061314.log");
	std::string contents;

        std::string strDateStart = "2014-08-01";
	std::string strDateEnd = "2014-08-10";
	contents = l.getLogs(strDateStart, strDateEnd);
	std::cout << "File content is: " << std::endl;
	std::cout << contents << std::endl;

//LReader.h

class LReader {

	public:
	LReader(const std::string & pth) : path(pth) { };
	std::string getLogs (const std::string & c, const std::string & d);


	private:
	
	std::fstream logFile;
	std::string path;

//LReader.cpp

std::string LReader::getLogs (const std::string & c, const std::string & d){

	std::ifstream logFile(path.c_str());


	 if (logFile.fail())
	 	    {
		 std:: cout << "Can't open file" << std::endl;
	 	        void exit ();
	 	    }
	 std:: string line2;

	 while (getline (logFile,line2) )
    {
		 std::size_t f1 = line2.find(c);
		 std::size_t f2 =line2.find(d);

		 if (f1!=std::string::npos )

			 f1++;
		 if ( f2!=std::string::npos)
			break;


		std::cout << line2 << std::endl;

    }

}



contents of /home/kaertech/stats_20140801_061314.log

2014-08-01 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-03 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-04 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-05 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-06 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-07 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-08 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-09 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-10 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-11 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-03 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-05 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-07 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-09 07:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 07:13:14,Name,4.5,CustomUnit,CustomType

Here's my output:

2014-08-01 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-02 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-03 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-04 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-05 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-06 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-07 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-08 06:13:14,Name,4.5,CustomUnit,CustomType
2014-08-09 06:13:14,Name,4.5,CustomUnit,CustomType
Segmentation fault (core dumped)

errors: it should display until 2014-08-10 and Segmentation fault (core dumped)



Another problem is I can't change main function and I also have a problem in returning my output to the main
Thanks for the suggestions
Last edited on
Look at line 32 then 39. They have the same name I would advise against this.

Also is there a reason you get the start and end date (c and d) each time in the loop? They aren't going to change. I also have no idea why you are incrementing f1.

Why don't you do something like:

1
2
3
4
5
6
7
8
9

std::string output = "";

while(std::getline(logFile, line2) line2.find(d) == std::string::npos)
{
    output += line2;
}

return output;


Oh you want to display until that so you would append line2 after the loop.

1
2
3
4
5
while(std::getline(logFile, line2) line2.find(d) == std::string::npos)
{
    output += line2;
}
output += line2;
Last edited on
giblit wrote:
Ugh I don't even know what you are trying to accomplish anymore.

Wild guessing, I suppose.

I told to use c <= x && x && <= d where x is a string derived from line2.
geng07's unmeticulous attempt was 0 <= line2 && line2 && <= 0

@geng07
The code fragment that you do show should not fault.

Your function should not write anything to cout either. It must return a string.
On another thread you did ask how to write only first N matching lines.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
string LReader::getLogs( const string & first, const string & last )
{
  string result {""};
  ifstream logFile( path );
  if ( ! logFile ) {
    cerr << "Can't open file " << path << '\n'; // #1
    return result;
  }
  string line2;
  const size_t Max {7};
  size_t count {0};
  while ( count < Max && getline( logFile, line2 ) ) // #2
  {
    const auto date { /*foo(line2)*/ }; // #3
    if ( first <= date && date <= last ) {
      ++count;
      // append line2 to result // #4
    }
  }
  return result;
}

Notes:
#1 Your program writes proper output to cout, so errors should not clutter it. IIRC, Windows hides the cerr though.

#2 If you only need Max first lines, then you don't read more.

#3 You have to figure out what expression the /*foo(line2)*/ should be. I have given a hint in earlier post.

#4 This is the one thing that you should do in all your getLogs functions. Does line2 contain a newline character?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
std::string LReader::getLogs (const std::string & c, const std::string & d){

	std::ifstream logFile(path.c_str());


	 if (logFile.fail())
	 	    {
		 std:: cout << "Can't open file" << std::endl;
	 	        void exit ();
	 	    }
	 std:: string line2;


	 std::string output = "";

	 while(std::getline(logFile, line2) && line2.find(d) == std::string::npos)
	 {
	     output += line2;
	 }




output:

File content is:
2014-08-09 06:13:14,Name,4.5,CustomUnit,CustomType
Ah I see now keskiverto they are wanting to output all the information in a range of [date1, date2] not all the dates until it found the "mystery date."

So you would have to get the date from the line then compare it to the desired ones you are checking.

Hints:

1) substr()
2) istringstream
3) std::getline

pick your poison.

Oh and I guess I shouldn't read half your post sorry keskiverto you already mentioned what the op needs to do.
Last edited on
i have problems in line 14 and line 9 @keskiverto
There is one fundamental question though.
The program should print:
1. all entries
2. one day's entries
3. entries from a range

op's current program reads the (same) file during each call to "fetch". The file could change (by other programs) between those calls. Each call thus uses "current" data and later calls could return entries that were not in earlier "all lines" call output.

It would be a different design, if the file would be read only once. Each "fetch" would assuredly filter same data.
my program should output entries from a range which is from 2014-08-01 to 2014-08-10 @keskiverto
Last edited on
Don't mean to be rude but he practically gave you the solution now you just have to put in a little bit of effort. If you have problems still post the code you have problems with. Maybe give http://www.cplusplus.com/forum/unices/140803/2/#msg746477 another shot at reading?
Pages: 123