3

How do I log more than a single string with log4cpp?

E.g. if I want to log all argv's to main:

#include <iostream>
#include <log4cpp/Category.hh>
#include <log4cpp/FileAppender.hh>
#include <log4cpp/PatternLayout.hh>

using namespace std;

int main(int argc, char* argv[]) {
    log4cpp::Appender *appender = new log4cpp::FileAppender("FileAppender","mylog");
    log4cpp::PatternLayout *layout = new log4cpp::PatternLayout();
    layout->setConversionPattern("%d: %p - %m %n");
    log4cpp::Category& category = log4cpp::Category::getInstance("Category");
    appender->setLayout(layout);
    category.setAppender(appender);
    category.setPriority(log4cpp::Priority::INFO); 

    category.info("program started"); // this works fine, I see it in the logfile

    for(int i=0; i<argc; ++i) {
        // next line does not compile:
        category.info("argv["<<i<<"] = '"<<argv[i]<<"'");
    }

    return 0;
}   

the line

category.info("argv["<<i<<"] = '"<<argv[i]<<"'");

does not compile. Obviously the logger does not work as a ostream. What is the log4cpp way to log something like this, preferable at once?

Jörg Beyer
  • 3,631
  • 21
  • 35

1 Answers1

7

You have two options:

  • Use printf-style formatting:

    for (int i = 0; i < argc; ++i)
    {   
        category.info("argv[%d] = '%s'", i, argv[i]);
    }  
    
  • Use infoStream():

    for (int i = 0; i < argc; ++i)
    {
        category.infoStream() << "argv[" << i << "] = '" << argv[i] << "'";
    }  
    

I'd go with the latter.

johnsyweb
  • 136,902
  • 23
  • 188
  • 247
  • that is: preformat a string (either with printf or ostringstream) and then log that string? – Jörg Beyer Mar 10 '12 at 11:01
  • @JörgBeyer: No pre-formatting required. Please see my updated answer. – johnsyweb Mar 10 '12 at 11:28
  • 1
    cool, the **category.infoStream()** is what I wanted but haven't found. – Jörg Beyer Mar 10 '12 at 11:29
  • How does infoStream() perform if no Info messages should be logged? Does it build the message and drops it afterward? I could imagine that the format version is faster in this case. – mmmmmmmm Mar 10 '12 at 11:40
  • @RüdigerStevens: I'm sorry, I've not looked at the implementation but if you are having performance issues, I recommend profiling. – johnsyweb Mar 11 '12 at 06:14
  • @Johnsyweb: I do not have any performance issues since our logging framework does not build any string if the log level is too high to log a message. BTW: Profiling does not work good if the you have 1000 places where strings are build and the dropped. You do not see any hot spot but your application is still slow :-) – mmmmmmmm Mar 14 '12 at 14:29
  • Is there any way to log the array values in one line? Log stream calls seem to append a newline after each statement... – thegeko Oct 04 '15 at 08:13