0

//Problem:Limit the instance of a class to one.

class Runtime{
    private static Runtime r;
    private Runtime(){
    System.out.println("In Runtime class.");
    }
    static{
    r=new Runtime();
    }
    static Runtime getRuntime(){
    Runtime r=new Runtime();
    return r;
    }
}

class TestRuntime{
    public static void main(String[] args) {
        Runtime r1;
        r1=Runtime.getRuntime();
    }
}

I want to understand what this code actually does, and how it limits the object creation. What could be the other possible solutions? Preferably in a manner this code solves the problem.

Nathan Hughes
  • 94,330
  • 19
  • 181
  • 276
KumarAnkit
  • 713
  • 1
  • 9
  • 26
  • This doesn't, it creates a new instance every time `getRuntime` is called – UnholySheep Oct 08 '17 at 11:02
  • 1
    What you seem to be looking for is the "Singleton Pattern", read e.g.: the [Wikipedia article](https://en.wikipedia.org/wiki/Singleton_pattern) for more information (and a very simple example) – UnholySheep Oct 08 '17 at 11:03
  • I found this post about the singleton pattern : https://www.javaworld.com/article/2073352/core-java/simply-singleton.html – JHDev Oct 08 '17 at 11:09
  • @UnholySheep, ok, but I want to know how this code works internally. Also, someone mentioned in the answer, here[https://stackoverflow.com/questions/2832297/java-singleton-pattern] that it is not safe. I want to know why and how it can be made safe? – KumarAnkit Oct 08 '17 at 11:11
  • the code you've posted seems faulty. It is not a singleton class. This'll create a new instance everytime getRuntime() is called. Instead, in the getRuntime method, 'r' should be returned directly. – Shubham Maheshwari Oct 08 '17 at 11:23
  • @ShubhamMaheshwari, Can constructors be static in java? – KumarAnkit Oct 08 '17 at 13:08
  • @KumarAnkit static is used to indicate something (member variable or method) that is at the class level. A constructor is already at the class level, so a static constructor does not make any sense. – Shubham Maheshwari Oct 09 '17 at 07:25

4 Answers4

1

Under the hood of JVM, you cannot really "prevent" creating more than one instance of a class. On the other hand, it's very common that you sometimes want to use same object everywhere in your code, because it just doesn't make sense to have more than one instance. So people came up with the idea of "singletons".

In Java, singletons are achieved by a trick that makes use of "static" modifier. By tagging something as "static", you tell the compiler that you want to have a single copy shared by all instances of that class. That makes the field per-class instead of per-instance. So unless you fiddle with custom classloaders or something like that, this also means you have a single copy in entire JVM.

Also, you need to make a constructor private, so that other code is not able to just call the constructor to create another instance.

However, you should keep in mind that this is only a "cosmetical" limitation enforced by compiler. Think of it as a good programming manners. One can still create other object through reflection, for example.

jurez
  • 4,436
  • 2
  • 12
  • 20
0

The code you've posted seems faulty. It is not a singleton class. This'll create a new instance every time getRuntime() is called. Instead, in the getRuntime method, 'r' (initialized in the static block) should be returned directly.

If you are looking for singleton pattern, take a look at the following implementation. https://en.wikipedia.org/wiki/Singleton_pattern#Lazy_initialization

0

First of all what you are asking is a very common issue. So common that it is called a "Singleton pattern" you can search for it and you will find more then enough info. As to your code it is almost good. Change your getRuntime() method to this and you will be fine (remove line r1=Runtime.getRuntime(); from getRuntime())

    static Runtime getRuntime(){
      return r;
    }

Now there are 2 major approaches to instanciating Singleton - Eager and Lazy.

  1. Eager means that your Singleton will be instanciated when your application starts up. This is what you did. Big "pro" is that it is strait forward and simple. a "con" would be that if your Singleton has a large footprint and takes a long time to initialize then your app will "waste" memory before it has to and will take a longer time to initialize.
  2. Lazy means that your Singleton gets created only when it actually requested for the first time. "Pros": Your Singleton dos not delay your app start up time and saves memory. "Con": The implementation is complex and treaky. Search the web to see why.
    However if you use some framework (Spring for instance) that takes care of managing all instanciations for you, all you will need to do is to say that a particular class must be a Singleton and instanciated lazily, so no complexity

    Basically, the recommendation is, that if you can afford for your Singleton to be instanciated eagerly (i.e. the cons of that method can be tolerated) then use this way. If this method is not acceptable for some reason, then use Lazy instanciation
Michael Gantman
  • 7,315
  • 2
  • 19
  • 36
0

A very basic implementation of a real Singleton would look like this:

public class Runtime {

    // a single(ton) instance to limit the instantiation to 1
    private static Runtime runtimeInstance;

    // a private constructor, not accessable from outside this class!
    private Runtime() {
        System.out.println("First creation of a Runtime instance.");
    }

    // the method that actually provides a single instance to callers
    public static Runtime getInstance() {
        // if the instance is not yet instanciated
        if (runtimeInstance == null) {
            // instanciate it with the private constructor
            runtimeInstance = new Runtime();
        }
        // return the instance
        return runtimeInstance;
    }
}

Then you are able to call the object by

Runtime runtime = Runtime.getInstance();

which always gives you the single instance.

deHaar
  • 17,687
  • 10
  • 38
  • 51
  • 1
    Definitely a faulty example. Several threads can get simultaniously to checking condition "if (runtimeInstance == null)" while it is still actually null and then each thread will create a new instance. This is classical example how NOT to write Singleton – Michael Gantman Oct 08 '17 at 13:04
  • I should have pointed out that this example is only meant to understand the basics of a Singleton, since the question was not at all about different threads. I vote your comment up because you are right, but in the context of this question your suggestion might be a little too much overhead… – deHaar Oct 08 '17 at 13:08
  • I understand your point, but disagree. Singleton basically implies a multithreaded environment, But I guess it is a fair point for debate. In any case it is very galant and large of you to upvote a point that is netgative toward your answer. Thanks. – Michael Gantman Oct 08 '17 at 13:14
  • In case anyone reads this and wants to get an idea of why this answer was (somehow justifiably) voted down, have a look at this question and its answers: https://stackoverflow.com/questions/11639746/what-is-the-point-of-making-the-singleton-instance-volatile-while-using-double-l There are several ways to make a Singleton thread safe… many of them stated in the answers to the linked question. – deHaar Oct 08 '17 at 13:38
  • To say that singletons are useful only in a multithreaded environment is just not correct, hence 1+ – dsp_user Oct 08 '17 at 17:35
  • A quick, obvious improvement would be marking `getInstance()` with `synchronized`. – Maow Jul 12 '21 at 19:56