(Not So) Stupid Questions 15: How Can a Constructor Be Private?
11/28/2006
Editor's note: Sometimes the most interesting discussions begin when someone says, "This may be a stupid question, but ...." If the person asking the question has taken the time to think about the problem before asking, the question is often not stupid at all. The uncertainty points out an ambiguity in the specs, holes in the docs, or a search for how more experienced programmers might address a particular problem. From time to time, we will print one of the "(Not So) Stupid Questions" we receive and invite our readers to answer the question in the feedback section.
Remember that new people are joining the Java community all the time and may be looking for help from those with more experience. Also, those who began with Java as their first language can benefit from those coming to the community with experience in other languages. As always, answer the questions with kindness. You are also welcome to submit your questions to
This may be a stupid question, but ... "How can a constructor be private?"
First thoughts:
Constructors, like other methods, can have the access modifiers public, protected, and private, or not have an access modifier at all. If a method is private, then other classes can't call the method--it can only be called from within the class itself.
All of this is true of constructors, just like other methods. So it's legal to write:
public class MyClass {
private MyClass() {
...
}
}
This will compile, but I don't see the point. The private modifier on the constructor prevents anything but an instance of this class from calling the constructor. But for there to be an instance at all, the constructor would have to be called somehow.
You would not BELIEVE how helpful it was for me to consciously DECIDE to ask questions with a girl tonight. It helped TREMENDOUSLY. I learned so much. It sounds so fucking simple but I talked SO much usually that I didnt get the info I needed so I could use that info back to her. mysteryseduceamogflirtpickup
pls help
2007-05-08 05:42:59 sougandika
[Reply | View]
hai
why we should not declare the top class and interfaces by using these modifiers static,protected,private .
we can use synchronize before the class and interface? what is the use of it? where we will use it?
It may lead to it performance issues depending how it was programmed. Java has a wide variety of methods to limit a threads locking. For example, I am using the collection CopyOnWriteArrayList because I know I won't be inserting into the array as much as I am trying to iterate through it. It doesn't actually lock the array either when adding to it; the array is copied on insert. The iterator might not have the most up to date list but thats the trade off.
A simple example
2006-11-30 12:48:57 ekt
[Reply | View]
A public constructor cannot constrain the number of instances of the class that are created. With a private constructor, you can insert some logic which may not allow a new instance.
The simplest example is a class which is supposed to be a singleton -- only one instance is allowed. This is a good idea in many situations, for example a resource controller that controls a single resource is likely to be a singleton.
Code
make the constructor private:
private Singleton() {};
make and attribute to keep track of the one and only instance if it exists
private Singleton myOnlyInstancel;
make a public method, say
public Singleton getSingleton() {
if myOnlyInstance == null {
myOnlyInstance = new Singleton;
}
return myOnlyInstance;
}
Utility classes (such as java.util.Collections) that typically only declare static methods do not need to be instantiated, a private constructor can be used to enforce this.
protection of inner class
2006-11-28 12:06:23 tim12s
[Reply | View]
You want to expose an inner class but ensure that only the outer class may construct the object.
This is illegal because the inner classes constructor is private:
Foo.Baa baa = foo.new Baa();
public class Foo {
class Baa {
private Baa() {
System.out.println("Baa()");
}
void doit() {
System.out.println("Baa.doit()");
}
}
public static void main(String[] args) {
Foo foo = new Foo();
foo.doit();
Boo boo = new Boo();
boo.doit(foo);
}
}
class Boo {
public void doit(Foo foo) {
Foo.Baa baa = foo.new Baa();
baa.doit();
}
}
protection of inner class
2006-11-28 21:35:54 completeajay
[Reply | View]
it help in the singleton pattern .the constructor instance is only one .U cannot make more than one instance of the same class in that case.
protection of inner class
2006-11-29 00:41:34 tim12s
[Reply | View]
Sometimes your inner classes contain privileged code. If you do not seal your packages or make your inner classes private then they can be hijacked. I'm refering to security topics you might have to consider if you were writing a container/app server.
protection of inner class
2006-11-30 07:10:10 tackline
[Reply | View]
If you were to allow potentially malicious code into your packages, I think it's game over anyway.
I'm not entirely convinced that making constructors private prevents malicious code from instantiating a subclass prior to 1.6 (even if it doesn't implement Serializable).
protection of inner class
2008-01-21 13:32:41 kramik1
[Reply | View]
I believe your right, if you mean by extending the class. Otherwise as long as the code is encapsulated correctly, another program cannot hack the data sets in that class, especially since the constructor is private. In order to stop from extending the class you can make it final. Final is actually very useful in a variety of situations.
Facades and Helpers
2006-11-28 09:04:11 beefspecial
[Reply | View]
I also use private constructors in Facades and Helper classes that have no non-static methods or properties.
public class MyHelper {
private MyHelper() { /* Helper Class */ }
public static String getHello() {
return "Hello"
}
}
interface ITypeSafeEnums {
final class MyTypeSafe {
// Enum Constants
public static final MyTypeSafe A = new MyTypeSafe("A");
public static final MyTypeSafe B = new MyTypeSafe("B");
only the default constructor is private
2006-11-28 06:30:10 coffeefavorites
[Reply | View]
Hi,
i use the private modifier for the default constructor if I want to make sure, that I can't instantiate an instance without setting a property:
class myClass {
private Object reallyNeeded;
private myClass() {};
public myClass(Object object) {
this();
this.reallyNeeded = object;
}
}
only the default constructor is private
2006-11-28 08:02:25 tjpalmer
[Reply | View]
There's no need to declare the private constructor in this case. If you make other constructors (but not a no-arg version), then there will be no no-arg constructor at all. The default no-arg constructor is only created when you don't have contructors of your own. And on a side note, since constructors aren't inherited (other than the potential optional default constructor calling super() if you don't supply a constructor of your own and if there's a no-arg super() to call), then even in the subclassing case, there's no need to make a private constructor here. But if you have actual content in your private no-arg contructor, there could be some value here.
Other replies on singletons (which I usually dislike but am often too lazy to avoid) and factory methods are related more to why you might want private constructors.
Or if all you have are static methods (like the Math class), you might also want a private constructor. This isn't quite the same as singletons, even though some of the usage feels similar.
only the default constructor is private
2007-03-06 12:32:50 amarpatil
[Reply | View]
you make other constructors (but not a no-arg version), then there will be no no-arg constructor at all.
You can't have class with a constructor that takes an arg without having default (no-arg) constructor declared. So in case you want to force the users to create objects by passing some args then the approach is to have default constructor declared as public.
only the default constructor is private
2007-03-06 12:36:22 amarpatil
[Reply | View]
It is mandatory to declare a default (no-arg) constructor, if you want to have constructors that take args.
only the default constructor is private
2007-03-06 12:40:54 amarpatil
[Reply | View]
I stand corrected, you "CAN" have classes without defualt (no-arg) constructor, but with arg constructors.
Private constructor can be called from inside the static methods.
2006-11-28 03:56:51 kishoresjava
[Reply | View]
Private constructors can be used in two ways, private constructor can be called by other constructors.
or private constructors can also be called from static methods.
To call a static method on a class you don't need an instance.
So a static method inside the class can create an instance of the class(Static method is inside the class so it will have access to private constructor also).
This is used in SingleTon design pattern.
Kishore.
Private constructor can be called from inside the static methods.
2006-11-28 05:06:31 mblua
[Reply | View]
"Private constructors can be used in two ways, private constructor can be called by other constructors.
or private constructors can also be called from static methods."
I don't understand this use of a private constructor. Why don't you just create other method? Is there any advantage or special use that needs a constructor?
Mariano Blua
(SAME - Sorry about my english)
Private constructor can be called from inside the static methods.
2006-11-28 13:37:07 afishionado
[Reply | View]
So you could do something like this:
public class Foo {
private Foo() {}
public static Foo createFoo {
if (itsOkayToCreateFoo()) {
return new Foo();
} else {
return null;
}
}
}
The static method doesn't *have* to return a Foo, but the constructor does.
The static "factory method" could do all kinds of things--it's possible to actually return a subclass of Foo instead of Foo itself. Random example:
public static createFoo {
if (isWindows()) {
return new Foo.WindowsFoo();
} else if (isMac()) {
return new Foo.MacFoo();
} else if (isLinux()) {
return new Foo.LinuxFoo();
} else {
return null;
}
}
Basically, the static factory method is more flexible than having programs call the constructor directly, but is slightly more complex, and confusing to new programmers. :-)
Private constructor can be called from inside the static methods.
2006-11-28 18:12:41 mblua
[Reply | View]
really thanks both! Good examples!
Private constructor can be called from inside the static methods.
2006-11-28 06:48:36 hcsoftware
[Reply | View]
If you don't provide any constructors, javac implicitly generates a public no-arg constructor.
So you might want to explicitly declare the constructor private to prevent other objects from instantiating it.
Useful for Singletons
2006-11-28 03:52:50 mmoraes
[Reply | View]
The singleton design pattern is used to restrict instantiation of a class to one object. It means, you will have only one instance per JVM.
For those classes is a good practice make a private contructor, ex:
public class MySingleTon {
private static MySingleTon instance;
private MySingleTon() {}
// factory method
public static MySingleTon getInstance() {
if (instance == null) instance = new MySingleTon()
return instance;
}
}
Does anyone knows more useful things to do with private contructors?
When using a factory method
2006-11-28 03:50:05 sbglasius
[Reply | View]
eg.
public class MyClass {
private MyClass() {
}
public static MyClass getInstance() {
return new MyClass();
}
}
or when having a class holding pure static methods:
public final class MyUtils {
private MyUtils {}
public static String myMethod() {
return ....;
}
}
I declared it final, as it's not supposed to be extendable.
/Søren
When using a factory method with an interface
2006-11-29 02:22:48 gruenewa
[Reply | View]
Using a private constructor and a factory method you can ensure that clients only access the interface. I often use this pattern:
/*
* This is an interface.
*/
public interface HelloService {
public abstract void sayHello();
}
/*
* This is an implementation with a factory method
*/
public class HelloServiceGerman {
private HelloServiceImpl() {}
public static HelloService getInstance() {
return new HelloServiceImpl();
}
public void sayHello() { System.out.println("Hallo"); }
}