{"id":2779,"date":"2018-03-21T16:21:25","date_gmt":"2018-03-21T16:21:25","guid":{"rendered":"http:\/\/codethataint.com\/blog\/?p=2779"},"modified":"2024-02-11T07:35:44","modified_gmt":"2024-02-11T07:35:44","slug":"item3-ensure-singleton-with-private-constructor","status":"publish","type":"post","link":"https:\/\/codethataint.com\/blog\/item3-ensure-singleton-with-private-constructor\/","title":{"rendered":"Enforce Singleton with private Constructor"},"content":{"rendered":"<p>While Implementing Singleton the following things should be answered<\/p>\n<ol>\n<li>Reflection<\/li>\n<li>Serialization<\/li>\n<li>Cloning<\/li>\n<\/ol>\n<p>Objects for Singleton Classes implemented using private Constructor can be invoked by <strong>Reflection<\/strong> as below <\/p>\n<p><strong>Item3.java<\/strong><\/p>\n<pre class=\"brush: java; title: ; notranslate\" title=\"\">\r\npackage com.mugil.org.ej;\r\n\r\nimport java.lang.reflect.Constructor;\r\n\r\npublic class Item3 {\r\n\tpublic static void main(String&#x5B;] args) \r\n\t{\r\n\t\t\/\/ reflection concept to get constructor of a Singleton class.  \r\n\t\tConstructor&lt;Singleton&gt; constructor;\r\n\t\t\r\n\t\ttry {\t\t\t\r\n\t\t\tconstructor = Singleton.class.getDeclaredConstructor();\r\n\t\t\t\r\n\t\t\t\/\/ change the accessibility of constructor for outside a class object creation.\r\n\t\t\tconstructor.setAccessible(true);\r\n\t\t\t\r\n\t\t\t\/\/ creates object of a class as constructor is accessible now.\r\n\t\t\tSingleton secondOb = constructor.newInstance();\r\n\t\t\tSystem.out.println(secondOb.getName());\r\n\t\t\t\r\n\t\t\t\/\/ close the accessibility of a constructor.\r\n\t\t\tconstructor.setAccessible(false);\r\n\t\t} catch (Exception e){\r\n\t\t\t\/\/ TODO Auto-generated catch block\r\n\t\t\te.printStackTrace();\r\n\t\t}\t\t\r\n\t}\r\n}\r\n\r\n\r\nclass Singleton {\r\n\r\n    private static Singleton instance = new Singleton();\r\n\r\n    \/* private constructor *\/\r\n    private Singleton() {}\r\n\r\n    public static Singleton getDefaultInstance() {\r\n        return instance;\r\n    }\r\n    \r\n    public String getName()\r\n    {\r\n    \treturn &quot;MyName&quot;;\r\n    }\r\n}\r\n<\/pre>\n<p><strong>Output<\/strong><\/p>\n<pre>\r\nMyName\r\n<\/pre>\n<p><strong>Singleton and Serialization<\/strong><br \/>\n<em>Without readResolve() Method<\/em><\/p>\n<pre class=\"brush: java; title: ; notranslate\" title=\"\">\r\n\/\/ Java code to explain effect of \r\n\/\/ Serilization on singleton classes\r\nimport java.io.FileInputStream;\r\nimport java.io.FileOutputStream;\r\nimport java.io.ObjectInput;\r\nimport java.io.ObjectInputStream;\r\nimport java.io.ObjectOutput;\r\nimport java.io.ObjectOutputStream;\r\nimport java.io.Serializable;\r\n \r\nclass Singleton implements Serializable \r\n{\r\n    \/\/ public instance initialized when loading the class\r\n    public static Singleton instance = new Singleton();\r\n     \r\n    private Singleton() \r\n    {\r\n        \/\/ private constructor\r\n    }\r\n}\r\n \r\n \r\npublic class GFG \r\n{\r\n \r\n    public static void main(String&#x5B;] args) \r\n    {\r\n        try\r\n        {\r\n            Singleton instance1 = Singleton.instance;\r\n            ObjectOutput out\r\n                = new ObjectOutputStream(new FileOutputStream(&quot;file.text&quot;));\r\n            out.writeObject(instance1);\r\n            out.close();\r\n     \r\n            \/\/ deserailize from file to object\r\n            ObjectInput in \r\n                = new ObjectInputStream(new FileInputStream(&quot;file.text&quot;));\r\n             \r\n            Singleton instance2 = (Singleton) in.readObject();\r\n            in.close();\r\n     \r\n            System.out.println(&quot;instance1 hashCode:- &quot;\r\n                                                 + instance1.hashCode());\r\n            System.out.println(&quot;instance2 hashCode:- &quot;\r\n                                                 + instance2.hashCode());\r\n        } \r\n         \r\n        catch (Exception e) \r\n        {\r\n            e.printStackTrace();\r\n        }\r\n    }\r\n}\r\n<\/pre>\n<p><strong>Output<\/strong><\/p>\n<pre>\r\ninstance1 hashCode:- 1550089733\r\ninstance2 hashCode:- 785945\r\n<\/pre>\n<p><em>With readResolve() Method<\/em><\/p>\n<pre class=\"brush: java; title: ; notranslate\" title=\"\">\r\n\/\/ Java code to remove the effect of \r\n\/\/ Serialization on singleton classes\r\nimport java.io.FileInputStream;\r\nimport java.io.FileOutputStream;\r\nimport java.io.ObjectInput;\r\nimport java.io.ObjectInputStream;\r\nimport java.io.ObjectOutput;\r\nimport java.io.ObjectOutputStream;\r\nimport java.io.Serializable;\r\n \r\nclass Singleton implements Serializable \r\n{\r\n    \/\/ public instance initialized when loading the class\r\n    public static Singleton instance = new Singleton();\r\n     \r\n    private Singleton() \r\n    {\r\n        \/\/ private constructor\r\n    }\r\n     \r\n    \/\/ implement readResolve method\r\n    protected Object readResolve()\r\n    {\r\n        return instance;\r\n    }\r\n}\r\n \r\npublic class GFG \r\n{\r\n \r\n    public static void main(String&#x5B;] args) \r\n    {\r\n        try\r\n        {\r\n            Singleton instance1 = Singleton.instance;\r\n            ObjectOutput out \r\n                = new ObjectOutputStream(new FileOutputStream(&quot;file.text&quot;));\r\n            out.writeObject(instance1);\r\n            out.close();\r\n         \r\n            \/\/ deserailize from file to object\r\n            ObjectInput in \r\n                = new ObjectInputStream(new FileInputStream(&quot;file.text&quot;));\r\n            Singleton instance2 = (Singleton) in.readObject();\r\n            in.close();\r\n         \r\n            System.out.println(&quot;instance1 hashCode:- &quot;\r\n                                           + instance1.hashCode());\r\n            System.out.println(&quot;instance2 hashCode:- &quot;\r\n                                           + instance2.hashCode());\r\n        } \r\n         \r\n        catch (Exception e)\r\n        {\r\n            e.printStackTrace();\r\n        }\r\n    }\r\n}\r\n<\/pre>\n<p><strong>Output<\/strong><\/p>\n<pre>\r\ninstance1 hashCode:- 1550089733\r\ninstance2 hashCode:- 1550089733\r\n<\/pre>\n<p>Refer <a href=\"http:\/\/Here\">http:\/\/codethataint.com\/blog\/singleton-and-serialization\/<\/a><\/p>\n<pre class=\"brush: java; title: ; notranslate\" title=\"\">\r\n\/\/ JAVA code to explain cloning \r\n\/\/ issue with singleton\r\nclass SuperClass implements Cloneable\r\n{\r\n  int i = 10;\r\n \r\n  @Override\r\n  protected Object clone() throws CloneNotSupportedException \r\n  {\r\n    return super.clone();\r\n  }\r\n}\r\n \r\n\/\/ Singleton class\r\nclass Singleton extends SuperClass\r\n{\r\n  \/\/ public instance initialized when loading the class\r\n  public static Singleton instance = new Singleton();\r\n \r\n  private Singleton() \r\n  {\r\n    \/\/ private constructor\r\n  }\r\n}\r\n \r\npublic class GFG\r\n{\r\n  public static void main(String&#x5B;] args) throws CloneNotSupportedException \r\n  {\r\n    Singleton instance1 = Singleton.instance;\r\n    Singleton instance2 = (Singleton) instance1.clone();\r\n    System.out.println(&quot;instance1 hashCode:- &quot;\r\n                           + instance1.hashCode());\r\n    System.out.println(&quot;instance2 hashCode:- &quot;\r\n                           + instance2.hashCode()); \r\n  }\r\n}\r\n<\/pre>\n<p><strong>Output<\/strong><\/p>\n<pre>\r\nOutput :- \r\ninstance1 hashCode:- 366712642\r\ninstance2 hashCode:- 1829164700\r\n<\/pre>\n<p>Two different hashCode means there are 2 different objects of singleton class.<\/p>\n<p>To overcome this issue, override clone() method and throw an exception from clone method that is CloneNotSupportedException. Now whenever user will try to create clone of singleton object, it will throw exception and hence our class remains singleton.<\/p>\n<pre class=\"brush: java; title: ; notranslate\" title=\"\">\r\n\/\/ JAVA code to explain overcome \r\n\/\/ cloning issue with singleton\r\nclass SuperClass implements Cloneable\r\n{\r\n  int i = 10;\r\n \r\n  @Override\r\n  protected Object clone() throws CloneNotSupportedException \r\n  {\r\n    return super.clone();\r\n  }\r\n}\r\n \r\n\/\/ Singleton class\r\nclass Singleton extends SuperClass\r\n{\r\n  \/\/ public instance initialized when loading the class\r\n  public static Singleton instance = new Singleton();\r\n \r\n  private Singleton() \r\n  {\r\n    \/\/ private constructor\r\n  }\r\n \r\n  @Override\r\n  protected Object clone() throws CloneNotSupportedException \r\n  {\r\n    throw new CloneNotSupportedException();\r\n  }\r\n}\r\n \r\npublic class GFG\r\n{\r\n  public static void main(String&#x5B;] args) throws CloneNotSupportedException \r\n  {\r\n    Singleton instance1 = Singleton.instance;\r\n    Singleton instance2 = (Singleton) instance1.clone();\r\n    System.out.println(&quot;instance1 hashCode:- &quot;\r\n                         + instance1.hashCode());\r\n    System.out.println(&quot;instance2 hashCode:- &quot;\r\n                         + instance2.hashCode()); \r\n  }\r\n}\r\n<\/pre>\n<p><strong>Output<\/strong><\/p>\n<pre>\r\nOutput:-\r\nException in thread \"main\" java.lang.CloneNotSupportedException\r\n\tat GFG.Singleton.clone(GFG.java:29)\r\n\tat GFG.GFG.main(GFG.java:38)\r\n<\/pre>\n<p>If you don;t want to throw exception you can also return the same instance from clone method.<\/p>\n<pre class=\"brush: java; title: ; notranslate\" title=\"\">\r\n\/\/ JAVA code to explain overcome \r\n\/\/ cloning issue with singleton\r\nclass SuperClass implements Cloneable\r\n{\r\n  int i = 10;\r\n \r\n  @Override\r\n  protected Object clone() throws CloneNotSupportedException \r\n  {\r\n    return super.clone();\r\n  }\r\n}\r\n \r\n\/\/ Singleton class\r\nclass Singleton extends SuperClass\r\n{\r\n  \/\/ public instance initialized when loading the class\r\n  public static Singleton instance = new Singleton();\r\n \r\n  private Singleton() \r\n  {\r\n    \/\/ private constructor\r\n  }\r\n \r\n  @Override\r\n  protected Object clone() throws CloneNotSupportedException \r\n  {\r\n    return instance;\r\n  }\r\n}\r\n \r\npublic class GFG\r\n{\r\n  public static void main(String&#x5B;] args) throws CloneNotSupportedException \r\n  {\r\n    Singleton instance1 = Singleton.instance;\r\n    Singleton instance2 = (Singleton) instance1.clone();\r\n    System.out.println(&quot;instance1 hashCode:- &quot;\r\n                           + instance1.hashCode());\r\n    System.out.println(&quot;instance2 hashCode:- &quot;\r\n                           + instance2.hashCode()); \r\n  }\r\n}\r\n<\/pre>\n<p><strong>Output<\/strong><\/p>\n<pre>\r\nOutput:-\r\ninstance1 hashCode:- 366712642\r\ninstance2 hashCode:- 366712642\r\n<\/pre>\n<p><strong>The Best way to implement Singleton is by using ENUM which takes care of Serialization and Other Issues on its own.<\/strong><\/p>\n","protected":false},"excerpt":{"rendered":"<p>While Implementing Singleton the following things should be answered Reflection Serialization Cloning Objects for Singleton Classes implemented using private Constructor can be invoked by Reflection as below Item3.java package com.mugil.org.ej; import java.lang.reflect.Constructor; public class Item3 { public static void main(String&#x5B;] args) { \/\/ reflection concept to get constructor of a Singleton class. Constructor&lt;Singleton&gt; constructor; try&hellip; <a href=\"https:\/\/codethataint.com\/blog\/item3-ensure-singleton-with-private-constructor\/\">Continue reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[245,227,64],"tags":[244],"class_list":["post-2779","post","type-post","status-publish","format-standard","hentry","category-effective-java","category-singleton","category-design-patterns","tag-effective-java"],"_links":{"self":[{"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/posts\/2779","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/comments?post=2779"}],"version-history":[{"count":9,"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/posts\/2779\/revisions"}],"predecessor-version":[{"id":2789,"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/posts\/2779\/revisions\/2789"}],"wp:attachment":[{"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/media?parent=2779"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/categories?post=2779"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/codethataint.com\/blog\/wp-json\/wp\/v2\/tags?post=2779"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}