• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Devaka Cooray
  • Ron McLeod
  • Paul Clapham
  • Liutauras Vilda
Sheriffs:
  • paul wheaton
  • Jeanne Boyarsky
  • Tim Cooke
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Tim Moores
  • Mikalai Zaikin
  • Carey Brown
Bartenders:

Singleton Class with Threads

 
Ranch Hand
Posts: 104
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
If a singleton is not thread safe, and two threads enter getInstance() at the same time, there are chances for getting two different objects, provided getInstance() is not synchronized. Is this true first of all. If so, how to recreate it? I did try with the below program,



and didn't see two different objects created,

Output is:
======
method in singleton class test.threads.SingleTonThreads@a90653
method in singleton class test.threads.SingleTonThreads@a90653
 
Ranch Hand
Posts: 174
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
There're plenty of discussions around about Singletons ... with several methods of achieving thread safety. I'd go with the 'construct at first class instantiation instead of getInstance method'.

In your case in the 'getInstance' method you check if 'tstt' is null. If the current thread isn't able to do the check, the instantioation and leaving the method (returning the singleton object) at once it is possible for another thread to get another instance of the singleton class. Try following code:
 
Ranch Hand
Posts: 525
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I don't understand the problem. Your singleton method seems to be working
fine. The two Thread objects, tt and tt1, each grab a reference to the same
SingltonThreads object. They each report this to you in the System.out.
Where do you see a problem?

Jim ... ...
 
Peter Taucher
Ranch Hand
Posts: 174
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
The problem is, that it's not thread-safe. Look into my example. It could happen that the curren thread is suspendend exactly inside the if clause but before returning a new instance. Another thread also calling getInstance would also run into the if clause and both reads may get different instances.
 
Jim Hoglund
Ranch Hand
Posts: 525
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Okay I see. So synchronize getInstance() or just the if() block.
It's very tough to get the JVM to swap threads in a particular place
and to another specific place, so I would just accept the risk as real
and do the synchronization. Also, the extra return statement is not
needed. Thanks.

Jim ... ...
 
author
Posts: 23942
142
jQuery Eclipse IDE Firefox Browser VI Editor C++ Chrome Java Linux Windows
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jim Hoglund wrote:
It's very tough to get the JVM to swap threads in a particular place
and to another specific place, so I would just accept the risk as real
and do the synchronization. Also, the extra return statement is not
needed. Thanks.



With modern processors, and how they all have multiple cores, it gets even more complicated. Don't think of it as having context switches that happen at particular locations. With these processors, the threads are truly running in parallel.

Henry
 
Vinney Shanmugam
Ranch Hand
Posts: 104
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Peter,

Thanks for the sample code. That's what I exactly wanted to write and didn't think of Thread.yield(). Your code solved my problem and cleared the air.



Thanks.
 
Ranch Hand
Posts: 384
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Henry Wong wrote:

Jim Hoglund wrote:
It's very tough to get the JVM to swap threads in a particular place
and to another specific place, so I would just accept the risk as real
and do the synchronization. Also, the extra return statement is not
needed. Thanks.



With modern processors, and how they all have multiple cores, it gets even more complicated. Don't think of it as having context switches that happen at particular locations. With these processors, the threads are truly running in parallel.

Henry



Yes Henry and moreover ... with more and more advanced core processors coming up in the future ... just imagine how wonderful it would be to program
 
Jim Hoglund
Ranch Hand
Posts: 525
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Henry : A question. How is the reality of multiprocessors reflected in Java 1.6,
and what do I need to know for about this for SCJP-6? Is it true that physically,
with multiple processors, there may be multiple threads running (with OS magic),
but logically, based on the language spec, thread behavior is as described above?

Jim ... ...
 
Ranch Hand
Posts: 144
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Peter Taucher wrote:



Still broken i think, should be :



or ofcourse as was mentioned :


 
R van Vliet
Ranch Hand
Posts: 144
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jim Hoglund wrote:Henry : A question. How is the reality of multiprocessors reflected in Java 1.6,
and what do I need to know for about this for SCJP-6? Is it true that physically,
with multiple processors, there may be multiple threads running (with OS magic),
but logically, based on the language spec, thread behavior is as described above?

Jim ... ...



The language spec is not in the way of true thread concurrency, you just have to keep in mind that there are some things you have to take into account with problems such as the above. Due to writes potentially happening out of order on the CPU level double check locking can still fail unless you force the VM not to keep track of references/variables in a thread local way. The volatile keyword does just that in this case.
 
Jim Hoglund
Ranch Hand
Posts: 525
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks. I have recently become a big fan of volatile and the "happens-before"
relationship that it guarantees. Have a great weekend!

Jim...
 
Rancher
Posts: 4803
7
Mac OS X VI Editor Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Any discussion of double checked access to singletons needs to point to a very nice, clear, article written by IBM thats shows how most "fixed" for singletons actually fail.

Double-checked locking and the Singleton pattern Note the subtitle of the article: "A comprehensive look at this broken programming idiom"

Its really a broken idiom, no matter that its described in the GOF book. I believe, very strongly, that Singletons are evil and should not be used, even with the "fixes" that the IBM article describes.

 
Jim Hoglund
Ranch Hand
Posts: 525
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Well I'm confused now. The IBM article by Peter Haggar claims that there is an unresolvable problem
with the singleton pattern. The foundation of his reasoning seems to be that "...thread B can preempt
thread A..." at certain critical moments, causing creation of more than one object, even if getInstance()
is synchronized. I suspect his conclusions, however, because the role of object locking in synchronized
methods is not discussed. If the Singleton class object will be locked before getInstance() can even
start, there can be no thread swaps; preventing preemption is the purpose of the lock. Am I missing
something here?

Jim ... ...
 
Pat Farrell
Rancher
Posts: 4803
7
Mac OS X VI Editor Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
If you use his hack, which is to have a inner class called something like SingletonHelper, then the rules of Java say that the instance of the Helper has to be completed, so your code is then thread safe. So you have fixed the double-check thread problem, which is widespread in most attempts to "solve" the problem.

Then you have to look at the bigger issue. You have a thread safe approach to implement a Singleton, but should you? And there, the answer is NO. A singleton is really a big glob of application wide global data. This tends to greatly increase coupling between modules. It specifically makes proper unit testing nearly impossible. You can't test a unit when it depends on a wad of global data. The state of the unit is not bound up in the unit.

There are approaches to this, often described as "dependency injection" but I hate that term, as most of the web pages that attempt to define it make it a ton more complex than it needs to be, and thus it scares away programmers from using it. This makes them fall back into using Singletons, which makes unit testing impossible.

There are simple, clean solutions that can and should be used instead of the evil Singleton pattern.
 
Master Rancher
Posts: 4660
63
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jim Hoglund wrote:Well I'm confused now. The IBM article by Peter Haggar claims that there is an unresolvable problem
with the singleton pattern.


No, he just says there's an unresolved problem with the double-checked locking idiom, which is one particular way of implementing a singleton. And he was quite correct back when this article was written in 2002. But the article is not correct now. The Java memory model was revised as of JDK 1.5, and using volatile with double-checked locking really does work. The brief editor's note referencing Brian Goetz' 2004 articles is also wrong - the referenced articles do not justify the flawed summary "the double-checked locking idiom is still broken under the new memory model". It's broken if you don't use volatile. It works fine if you do use volatile.

Jim Hoglund wrote:I suspect his conclusions, however, because the role of object locking in synchronized
methods is not discussed. If the Singleton class object will be locked before getInstance() can even
start, there can be no thread swaps; preventing preemption is the purpose of the lock. Am I missing
something here?


If you're locking the class object right at the outset of the getInstance() method, that's not double-checked locking - it's regular synchronization. It works, but it's more prone to bottleneck in cases of heavy thread contention. Which is a non-issue most of the time, but sometimes becomes a serious enough issue that people spend a lot of effort trying to avoid it.

I'm not a big fan of singletons - they were dreadfully overused ever since the Gang of Four book came out, and in many cases they're unnecessary or even counterproductive. And they were badly implemented for years. Double-checked locking, in particular, was a longtime source of bugs. Nonetheless, it is possible to use it in a thread-safe manner now. Whether you should, or whether you need a singleton at all, is another matter.
 
Pat Farrell
Rancher
Posts: 4803
7
Mac OS X VI Editor Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Mike Simmons wrote: they were dreadfully overused ever since the Gang of Four book came out, and in many cases they're unnecessary or even counterproductive.



Yes, the GoF book had some good stuff, but Singletons was not one of the good ideas.

I will argue that they are never necessary or even good. But that is a bit OT.
 
Jim Hoglund
Ranch Hand
Posts: 525
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Pat : I am not steeped in Java history, or tangled up in any of its
religious wars. (On JavaRanch some pretty strong feelings seem to
come out at times.) So I'm curious about problems with singletons.
Why should they be avoided?

Jim ... ...
 
Pat Farrell
Rancher
Posts: 4803
7
Mac OS X VI Editor Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jim Hoglund wrote:So I'm curious about problems with singletons. Why should they be avoided?


I thought I did a good high level explanation of why just a few posts upthread.

We can go into more detail, but probably should start a fresh thread in a better section.
 
I'm just a poor boy, I need no sympathy, because I'm easy come, easy go, little high, little low, little ad
a bit of art, as a gift, the permaculture playing cards
https://gardener-gift.com
reply
    Bookmark Topic Watch Topic
  • New Topic