Read last line text file

Pages: 12
Guys need some help,
I am making a script to read the latest from a text file. the script already does this but I'm kind of lost to adjust some things

He picks up the line by numbytes in fseek, but the data line may vary and numbytes not be accurate, how can I fix this?

And another problem is that the line has, date, time, value, separated by space, how to read that line and put these 3 information in variable?

#include <stdio.h>
#include <conio.h>

int main()
{
FILE *arq;
char Line[100];
char *result;
int tam, i;
// Opens a file for READING TEXT
arq = fopen("temp.txt", "rt");
if (arq == NULL) // If there was an error in opening
{
printf("Problems opening file\n");
return 2;
}
// Read last line text file
tam= -25;
fseek(arq, tam, SEEK_END);
i = 1;
while (!feof(arq))
{
result = fgets(Line, 100, arq);
if (result) // If it was possible to read the report online content
printf("%d : %s",i,Line);
i++;
}
fclose(arq);
}
Please use code tags. The <> button...
I would use fstream.
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
#include <iostream>
#include <fstream>

using namespace std;

int main()
{
        char * data1,data2,data3;
	fstream file; // If you don't know what std::fstream is, look it up
	file.open("temp.txt");
	if(!file.is_open())
	{
		cout << "Problem opening file.\n";
		return 2;
	}
	file.seekg(EOF); // go to the end of file
	while(true)
	{
		file.unget(); //go back two chars
		file.unget();
		char in = file.get();
		if(in == '\n')
		{
                        //get line from file until space is encountered and put it in data1
			file.getline(data1,' ');
                        file.getline(data2,' '); //etc
                        file.getline(data3,' ');//etc
			break;
		}
	}
        //send the data to the output stream
	cout << "Data: " << data1 << " " << data2 << " " << data3 << endl; 
        //end program
	return 0;
       
}


I pretty much typed this up in my browser, not guarranteed to work, but pretty sure it does. Hope this helps!

-SDude
Superdude wrote:
I pretty much typed this up in my browser, not guarranteed to work, but pretty sure it does. Hope this helps!

Just glancing at it, I can guarantee it won't work.


Here's something that will.
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
#include <iostream>
#include <fstream>
#include <string>

std::string getLastLine(std::ifstream& in)
{
    std::string line;
    while (in >> std::ws && std::getline(in, line)) // skip empty lines
        ;

    return line;
}

int main()
{
    std::ifstream file("temp.txt");

    if (file)
    {
        std::string line = getLastLine(file);
        std::cout << line << '\n';
    }
    else
        std::cout << "Unable to open file.\n";
}


or, a tiny bit more efficient:
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
#include <iostream>
#include <fstream>
#include <limits>
#include <string>

std::istream& ignoreline(std::ifstream& in, std::ifstream::pos_type& pos)
{
    pos = in.tellg();
    return in.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
}

std::string getLastLine(std::ifstream& in)
{
    std::ifstream::pos_type pos = in.tellg();

    std::ifstream::pos_type lastPos;
    while (in >> std::ws && ignoreline(in, lastPos))
        pos = lastPos;

    in.clear();
    in.seekg(pos);

    std::string line;
    std::getline(in, line);
    return line;
}

int main()
{
    std::ifstream file("temp.txt");

    if (file)
    {
        std::string line = getLastLine(file);
        std::cout << line << '\n';
    }
    else
        std::cout << "Unable to open file.\n";
}
Last edited on
Superdude and cire thank you for help

The code below worked fine, good even, but I need one more help

The "line" returns 3 values​​, date, time and value, how can I get these 3 values ​​and put in 3 variables?

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
#include <iostream>
#include <fstream>
#include <limits>
#include <string>

std::istream& ignoreline(std::ifstream& in, std::ifstream::pos_type& pos)
{
    pos = in.tellg();
    return in.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
}

std::string getLastLine(std::ifstream& in)
{
    std::ifstream::pos_type pos = in.tellg();

    std::ifstream::pos_type lastPos;
    while (in >> std::ws && ignoreline(in, lastPos))
        pos = lastPos;

    in.clear();
    in.seekg(pos);

    std::string line;
    std::getline(in, line);
    return line;
}

int main()
{
    std::ifstream file("temp.txt");

    if (file)
    {
        std::string line = getLastLine(file);
        std::cout << line << '\n';
    }
    else
        std::cout << "Unable to open file.\n";
}
Thanks cire for the correction.
This (should) work for splitting the data into three vars.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
string vars[3];
int whichVar = 0;
for(unsigned int i = 0; i < line.size(); i++)
{
        if(!line[i] == ' ')
        {
               vars[whichVar] += line[i]; //add the non-space char to the current
//variable        }
        else
        {
               whichVar++; //switch the variable being used
        }

}


This will only work as long as there are no spaces besides the separating ones. This will work if there is only two data members as well. or five, six, or seven, just change the size of the array.

Cire, if this is wrong too, please correct. ;)
Superdude believe have put this in the correct part of your code, fix the lack of "}" but n...
Could you elaborate?
a better way for doing the splitting:
1
2
3
4
5
6
7
std::string::size_type tmp;
std::vector<std::string> values;
for (std::string::size_type tmp=i=0; i!=std::string::npos; tmp=i)
{
    i=line.find(' ',tmp);
    values.push_back(std::string(tmp,i-tmp);
}
Last edited on
Superdude not understand how the code would look with your mod or the theranga
1
2
std::istringstream input( the_last_line );
input>>date>>time>>value;
1
2
std::istringstream input( the_last_line );
input>>date>>time>>value;


ne555
tested not working well

example the last line:
"17/7/2013 12:37:20 19,625"

script return using your suggestion
"17
0
1.32657e-315"
ne555
tested not working well

example the last line:
"17/7/2013 12:37:20 19,625"

script return using your suggestion
"17
0
1.32657e-315"
Report


Date and time are not numbers. Why are you attempting to extract them as if they are?


1
2
std::string date, time, value ;
input >> date >> time >> value ;
Last edited on
for me at least I think I got a better way to split the data, however I am having trouble splitting time and value, I do not think one way of defining reliable, can you 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
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
#include <iostream>
#include <fstream>
#include <limits>
#include <string>
#include <sstream>
#include <stdlib.h>

std::istream& ignoreline(std::ifstream& in, std::ifstream::pos_type& pos)
{
    pos = in.tellg();
    return in.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
}

std::string getLastLine(std::ifstream& in)
{
    std::ifstream::pos_type pos = in.tellg();

    std::ifstream::pos_type lastPos;
    while (in >> std::ws && ignoreline(in, lastPos))
        pos = lastPos;

    in.clear();
    in.seekg(pos);

    std::string line;
    std::getline(in, line);
    return line;
}

int main()
{
    std::string var1;
    std::string var2;
    std::string var3;
    std::ifstream file("temp.txt");

    if (file)
    {
        std::string line = getLastLine(file);
        
 	std::istringstream iss(line);
        getline(iss, var1, ' ');
        std::cout << var1 << '\n';
        getline(iss, var2, ' ');
        std::cout << var2 << '\n';
        getline(iss, var3, ' ');
        std::cout << var3 << '\n';
    }
    else
        std::cout << "Error\n";
        return 2;
}


example the last line:
"17/7/2013 12:37:20 19,625"

script return
17/7/2013
12:37:20 19,625

Any solution?
in the text file, you could put a ':' or other char to separate the two. Then on the input, check for that char.
He would have troubles with the time.
He already has whitespaces to separate them, so he should use whitespaces for that.
I managed to finish, grace your help, thanks to all who contributed.

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
#include <iostream>
#include <fstream>
#include <limits>
#include <string>
#include <sstream>
#include <stdlib.h>

std::istream& ignoreline(std::ifstream& in, std::ifstream::pos_type& pos)
{
    pos = in.tellg();
    return in.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
}

std::string getLastLine(std::ifstream& in)
{
    std::ifstream::pos_type pos = in.tellg();

    std::ifstream::pos_type lastPos;
    while (in >> std::ws && ignoreline(in, lastPos))
        pos = lastPos;

    in.clear();
    in.seekg(pos);

    std::string line;
    std::getline(in, line);
    return line;
}

int main()
{
    std::string var1;
    std::string var2;
    std::string var3;
    std::ifstream file("temp.txt");

    if (file)
    {
        std::string line = getLastLine(file);
        
 	std::istringstream iss(line);
        getline(iss, var1, ' ');
        std::cout << var1 << '\n';
        getline(iss, var2, '\t');
        std::cout << var2 << '\n';
        getline(iss, var3);
        std::cout << var3 << '\n';
    }
    else
        std::cout << "Error\n";
        return 2;
}
1
2
3
    else
        std::cout << "Error\n";
        return 2;


Are you aware that this will cause the app to exit with a status code of 2, regardless of whether the condition on line 37 is true or false?
to fix some of this, thanks

leveraging would like to see one more question,

I am trying to convert the string to double using:
"var4 = Convert.ToDouble (var3);"

But I get the error

[Error] 'Convert' was not declared in this scope
Well? Is it declared anywhere in your code?
Pages: 12