Recently, I have been working with XML parsers. This is just beginning for me and I managed to understand how to use DOM parser classes in java i.e. DocumentBuilderFactory
and DocumentBuilder
to parse an XML document.
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
DocumentBuilder db = dbf.newDocumentBuilder();
What I am asking myself is how come an abstract classes, such as DocumentBuilderFactory
and DocumentBuilder
, are allowed to instantiate new instances? And then in another example I see:
Calendar calendar = Calendar.getInstance();
System.out.println(calendar.get(Calendar.DATE));
- As far as I know, you can not instantiate (in other words, create an object) for abstract and interface classes. Am I correct?
- Do
getInstance()
and newInstancce()
methods create instances of the above abstract classes?
Am I missing something about using an abstract class and its new Objects?
That method is an abstract factory method, which returns a subclass of DocumentBuilder
, which is a (concrete) implementation.
The exact class of the object is not important to know, you only need to know that it's a DocumentBuilder
. The method may return an instance decided at runtime, or predetermined as it sees fit.
If you are curious to know, you can print out the actual class like this:
System.out.println(dbf.getClass());
Note that the method newInstance()
is not to be confused with the method of the same name of Class
, ie these two are different:
// a static method of this class
DocumentBuilderFactory.newInstance();
// an instance method of Class
DocumentBuilderFactory.class.newInstance();
An unfortunate choice of name sure to have caused confusion.
That is a static abstract factory method , which will return a subtype of DocumentBuilderFactory
not the actual instance of DocumentBuilderFactory
itself.It is not like what I presume, you understand :
DocumentBuilderFactory dbf = new DocumentBuilderFactory();
DocumentBuilderFactory#newInstance() , Obtain a new instance of a DocumentBuilderFactory. This static method creates a new factory instance. This method uses the following ordered lookup procedure to determine the DocumentBuilderFactory implementation class to load.
newInstance()
will return an instance of the implementing class(subtype) of DocumentBuilderFactory
, which is not abstract and will assign reference to that object to
DocumentBuilderFactory
reference variable.
It's a static method. You can call static methods of abstract(or any class for that matter) classes without a reference to an instance..
Thanks for everyone, after trying below code my doubt got cleared.
Calendar cls = Calendar.getInstance();
Date dt = new Date();
System.out.println(cls.getClass()); //<------ 1
DocumentBuilderFactory dbls = DocumentBuilderFactory.newInstance();
System.out.println(dbls.getClass()); //<------2
DocumentBuilder db = dbls.newDocumentBuilder();
System.out.println(db.getClass()); //<--------3
And I see the follwoing output:
********Output******
class java.util.GregorianCalendar
class com.sun.org.apache.xerces.internal.jaxp.DocumentBuilderFactoryImpl
class com.sun.org.apache.xerces.internal.jaxp.DocumentBuilderImpl
a) static method "DocumentBuilderFactory.newInstance()" returns subtype class instance called "DocumentBuilderFactoryImpl" .
b) "DocumentBuilderFactoryImpl" is a subclass of abstract "DocumentBuilderFacotory" class ,hence there is no problem if I give :
DocumentBuilderFacotryImpl dbls = DocumentBuilderFactory.newInstance();
//-----Instead of giving DocumentBuilderFactory dbls = DocumentBuilderFactory.newInstance();
and same applies to DocumentBuilderImpl db = dbls.newDocumentBuilder();
//---- Instead of DocumentBuilder db = dbls.bewDocumentBuilder();
Conclusion: newInstance(), newDocumentBuilder(), getInstance() returns subclass object. Although abstract class can not create new Object , we can assign subclass object to abstract class (i.e.parent) reference variable. ex:
Abstract class A{
}
class B extends A{
}
we can say:
A a = new B();
but not
A a = new A();