Hi,
Can anybody give me a hint on how to add a counter inside the logfile?
For example, if at first, the log file was created, it will write the current counter number, let say Log1. Everytime the application is open/launch the loop start and writes Log1, Log2, Log3, Log4 and so on for the same log filename if exist. If the file does not exist or let say a new log file was created the counter will reset to 1 and write this counter number to log file as well as the next number in the loop.

I used the below code snippet to open/create a log file.

m_oLogFileStream.open(pcLog, ios::out|ios::app|ios::in, filebuf::sh_read|filebuf::sh_write);

hope you can help me on this

thanks & regards
gilmar

u can store the counter value at the end of the log file. Next time its opened, goto the end and read that value, increament it, and write to the file after writting everything else in it.

Let me explain:
Lets start with an empty logfile.
Since it doesnot exists, u create one. Write all the logs u want in the file. Write 1 at the end. or use some format like "<<1>>". So that u can differentiate it from other logs written to the file.
Close the file.

When u reopen the file next time, it already exists. Now goto the end. Read <<1>>. U will get the 1 from here. Write all the log entries to the log file. At the end write <<2>>. and so on.
and so on .........

U can use any format (such as (1), [1], $1, etc.) of your wish which u can distinguish from a normal log message.

u can store the counter value at the end of the log file. Next time its opened, goto the end and read that value, increament it, and write to the file after writting everything else in it.

Let me explain:
Lets start with an empty logfile.
Since it doesnot exists, u create one. Write all the logs u want in the file. Write 1 at the end. or use some format like "<<1>>". So that u can differentiate it from other logs written to the file.
Close the file.

When u reopen the file next time, it already exists. Now goto the end. Read <<1>>. U will get the 1 from here. Write all the log entries to the log file. At the end write <<2>>. and so on.
and so on .........

U can use any format (such as (1), [1], $1, etc.) of your wish which u can distinguish from a normal log message.

Wow, thank you so much for the detailed explanation.
This means I have to parse the logfile, read the contents of the log line by line until the counter value found at the end of the file, if found store it in the variable and start incrementing. Read first the contents of the logfile before writing anything?

thanks
gilmar

Wow, thank you so much for the detailed explanation.
This means I have to parse the logfile, read the contents of the log line by line until the counter value found at the end of the file, if found store it in the variable and start incrementing. Read first the contents of the logfile before writing anything?

thanks
gilmar

absolutely..............

Do you really need to use a counter in your log file?

If it's something that's been specified for your project and you absolutely have to use it, then I guess you aught to do something like dkalita has suggested. If this is the case then ignore everything below as it is completely irrelevant and I'm sorry for wasting both space and time!

However if it's not necessary, would it make more sense to use a timestamp in your log file? So each time you write something to your log file you write out a little header with a timestamp?

Before you go panicking about getting the date/time, I've written my own little logger class which I use to debug some of my Windows projects and it uses timestamps. I'll take you through some of the relevant code to give you some ideas you can use for logging stuff in your own apps.

My logger class (JasLogger) is a header only file. So all of the code is in the header...Saves me having to include the .cpp file in my projects! I usually just include the header while debugging my project and once I'm done I remove the header and any instances of the logger. But I do also use it as a permanent logging mechanism in some projects too!

Anyway, the main point is I've written a little bit of code in it which allows the creation of a timestamp in the log.

Here's a snippet from the header file...The following are public member functions of my logger class..Because they are all defined in the header file there's no need to prepend the class name ( JasLogger:: ) to the function name.
These are the most relevant bits related to the timestamp:

/////////////////////////////////////////////////////////////
	///	Add a string to the Log...
	/////////////////////////////////////////////////////////////
	void AddString(std::string str)
	{
		if(logBuffer)
			logBuffer << str;
		else
			ShowError();
	};

	/////////////////////////////////////////////////////////////
	///	Add a timestamp string to the Log...
	/////////////////////////////////////////////////////////////
	void AddTimeStamp()
	{
		std::string stamp;
		GetTimeStamp(stamp);
		logBuffer << stamp << std::endl;
	};

	/////////////////////////////////////////////////////////////
	///	copies a datestamp into a std::string 
	/////////////////////////////////////////////////////////////
	void GetTimeStamp(std::string& stamp)
	{
                // Note: '#include <ctime>' for _strdate and _strtime 
		char date[10], time[10];
		_strdate(date);
		_strtime(time);

		stamp = (std::string)date + (std::string)" - " + (std::string)time;
	};

The 'logBuffer' variable mentioned above is a std::ostringstream object which is a public member of the class. This temporarily stores the strings that are eventually output to the log file!

The AddString() function..Well that just adds strings to the logBuffer object. Not really related to the timestamp, but this is the main way of adding strings to the log!

The GetTimeStamp() function is the function you're probably most interested in, this simply gets the date and time from the system as c style strings and copies them into the passed-in std::string object (stamp) .

The AddTimeStamp() function creates a new string object (stamp), calls GetTimeStamp passing stamp as a reference. GetTimeStamp then populates stamp with the timestamp. stamp is then output to the logBuffer.

Now we'll take a look at how I'd use the JasLogger class in day to day usage: (Note: This function was made up on the spot, so this isn't from anything in particular!)

double someFunction(double val1, double val2, double val3, bool flag)
{
    // calculate some value....
    double someVariable;
    if(flag)
    {    // I don't know what this is
        someVariable = (val1 * val2) + val3;
    }
    else
    {    // I'm making this up on the fly!
        someVariable = (val1 + val3) * (val2 + val3) / (val1 + val2);
    }

    // now I want to log the values in the function...
    // Creates a log file called DEBUGLOG.LOG on my desktop.
    JasLogger *pLog = new JasLogger();
    pLog->AddString("Log created: ");          // output a header
    pLog->AddTimeStamp();                      // and a timestamp

    // Now lets log some data.....
    pLog->AddString("Flag is ");              // output value of flag
    if(flag)
        pLog->AddString("True\n");
    else
        pLog->AddString("False\n");

    // output the value of someVariable
    pLog->logBuffer << "someVariable = " << someVariable << endl << endl;

    delete pLog;   
// code in the destructor creates/opens the file,
// dumps the logBuffer to the file and destroys the logger instance.

    return someVariable;
}

Each time someFunction is called an instance of my logger class is created. The timestamp and some data is logged and the default file (DEBUGLOG.LOG) is opened on my desktop....NOTE: The file is opened in append mode...So if the file doesn't exist, it is created, if it does exist it is appended to.

OK, so after running our imaginary application for a while, we'd expect the the above function we're logging to be called several times, so when you open the log-file (DEBUGLOG.LOG) on the desktop you'd see a log that looks like this:

Log created: 10/09/09 - 10:48:50
Flag is True
someVariable = 5.45674839459

Log created: 10/09/09 - 10:49:36
Flag is False
someVariable = 0.9255543453

Log created: 10/09/09 - 10:54:54
Flag is True
someVariable = 7.2934854345

So by using a timestamp, you and your program do not need to know how many times the logger has been fired off; Your app can just merrily log things without having to parse the log file each time it accesses the log. And by looking at the timestamps in the log-file, you or your users can see that the logged function has been called three times by the app. (Once at 10:48:50, again at 10:49:36 and finally at 10:54:54.)

Like I said at the very top of the post, I'm not sure if this is of any use to you, but it's an alternative to using a counter and it would save having to parse the log each time it's accessed.

By the way, I'm not suggesting that you need to make a logger class either. This was just a quick look at how I've created my own logger class, how I use it to create timestamps in my logs and how timestamps could possibly make your life a little easier...

The reason I created my class was because I find myself needing to log lots of things in various projects and applications. So instead of writing the same code over and over again, I've got everything I need in one place and I can reuse it over and over again.

If you're just creating a one off log file on the fly in your app, you could just use something like the code my GetTimeStamp() function to generate a timestamp; then open your log file in append mode, output a little header string (e.g. "Log created: ") along with your timestamp and then log any data before closing the file again.

Anyways, I hope this is of some use to you!
Cheers for now,
Jas.

Edited 7 Years Ago by JasonHippy: n/a

it was really a helpful post ..what changes i should do in JasLogger class ..
thanks for reply

if you are inside windows then you can use the registry to store that information.

if you are in linux use the file
/etc/<your-app-name>.conf

and store that variable inside that file.

This article has been dead for over six months. Start a new discussion instead.