Question

I would like opinion on this to settle a small dispute. Any help would be greatly appreciated.

I have written my own file handler that is attached to the logger. This being a file handler and being accessed by multiple threads, I am using synchronization in order to ensure that there is no collision during the writing process. Additionally it is a rolling log, so I also close and open files, and do not want any problems there either.

His response to it was (as pasted from email)

I strongly believe that Synchronization is very bad in the Handler. It is too complex for such easy task. So, I would say why do not use one instance per Thread?

What would you say is better from performance's and memory management perspective. Thank you very much for any response. Whenever writing and reading is involved in multithreaded applications I have used synchronization on java applications all my life, and have not heard of any severe performance issues.

So please I would like to know if there are any issues and I really should switch to one instance per thread.

And in general, what would be the downfall of using synchronization?

EDIT: the reason why I wrote a custom file handler (yes I do love slf4j), is because my custom handler is dealing with two files at once, and additionally I have few other functions I perform on top of writing to files.

Was it helpful?

Solution 2

As with all I/O, you have little choice but mutual exclusion. You may theoretically build up a complex scheme with a lock-free queue which accumulates logging entries, but its utility, and especially its reliability, would be very questionable: without careful design you could get a logging-caused OOME, have the application hang on due to threads which you didn't clean up, etc.

Keep in mind that, assuming you are using buffered I/O, you already have an equivalent of a queue, minimizing the time spent occupying the lock.

OTHER TIPS

another solution would be to use a separate thread to do the (costly on its own) writing and use concurrent queues to pass the log messages from the domain threads

the key part here is that pushing to a queue is much less costly that writing to a file and means that there is less interference from concurrent log calls

the call to log would then log like

private static BlockingQueue logQueue = //...

public static void log(String message){
//construct&filter message
    logQueue.add(message);
}

then in the logger thread it will look like

while(true){
    String message = logQueue.poll();
    logFile.println(message);//or whatever you are doing
}

The downfall to synchronisation is the fact that only one thread can access that part of the code at any one time, meaning your code will see little benefit from multithreading I.e. the synchronised part of your application will only be as fast as a single thread. (Small overhead for handling the synchronised status too, so a little slower perhaps)

However, in subjects where you don't want the threads to interfere with one another, such as writing to files, the security gained from the synchronisation is paramount, and the performance loss should just be accepted.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top