You could add a static counter to the class, and when it reaches the maximum count you can throw an exception in the constructor.
Or you can use a Singletonpattern. It is typically used to retrict the number of objects created by a class to one, but it could be used just as well to restrict the number object created by the class to any other amount.
Why would someone create more than three instances, and what bad would happen as a consequence? Do you really need to enforce the "only 3 instances" constraint?
The soul is dyed the color of its thoughts. Think only on those things that are in line with your principles and can bear the light of day. The content of your character is your choice. Day by day, what you do is who you become. Your integrity is your destiny - it is the light that guides your way. - Heraclitus
Well, it looks like the post has been edited a couple times, first by Paul S (adding code tags maybe?), then by Sudhakar. I assume Paul's comment probably reflects what the code looked like at the time he made the comment. Certainly the "Static int i=0;" and random changes in indentation seem to indicate that there might have been other errors present originally, as this code wouldn't even compile. Unless it changes again after I write this...
That implementation of the 'tringleton' pattern seems return the 3rd element in all invocations except the first two. Perhaps a better implementation would be the 'random tringleton' or even the 'round-robin tringleton'. Also, the variable 'i' should probably be synchronized, so maybe the 'synchronized round-robin tringleton' is in order.
Correct me if I'm wrong, but I believe there are three other ways (not including a separate VM) that the class could still be instantiated.
1. Serialization 2. Loaded by different class loaders 3. Synchronization error
With #1, they take the object (a singleton), serialize it with two diff. ObjectOutputStreams and then deserialize both into the same VM and voila - two objects of that type.
With #2, if you have classloaders not in the same hierarchy, they will treat them as completely different classes (not sure how to solve this one) and allow you to create 3 copies for EVERY classloader you create (outside each other's hierarchy).
(with #3, since the static method has no synchronization, two singletons will be created at the same time if while one's constructor is running, simultaneously another thread calls the method.)
To be fair, serialization is only an issue if the class implements Serializable, which in the code shown, it doesn't. If it did, then it would be necessary to implement a readResolve() method to control how (or whether) deseriallization takes place. I can't really think of any reason why it might be a good idea to allow a class like this to implement Serializable in the first place though, as it seems inherently contradictory with the idea of limiting instances.
[Dan]: 3. Synchronization error
As Steve Souza pointed out, though not in detail.
Another possible way to get an extra instance is with reflection, which can often be used to violate the private access modifier. Just call Constructor.setAccessible(true) - unless there's a SecurityManager configured to prevent this. Even this, though, can be prevented by coding the constructor to throw an exception if there are already three instances created. Under most circumstances that strikes me as being unnecessarily paranoid, but the option's there I suppose.
Joined: Jul 11, 2001
Originally posted by steve souza: That implementation of the 'tringleton' pattern seems return the 3rd element in all invocations except the first two. Perhaps a better implementation would be the 'random tringleton' or even the 'round-robin tringleton'.
Perhaps. What would be a good implementation of course depends on why we actually want to only have three instances, and what we want to do with them.
Until the original poster answers that question, the discussion is hopelessly bound to be purely academical, I fear.