11 Replies Latest reply: Feb 19, 2008 3:05 PM by 807601 RSS

    static initializers

    807601
      Hi everyone,

      it seems that statics has been one of the hardest topics for me to grasp in practical java... I am wondering about the following: When it comes to initialize/instantiate a static variable, are the next two approaches identical?
      class MyClass{
      private static Resource res = new Resource();
      
      //rest of code that uses the res reference goes here 
      }
      And then do it in a static initialization block:
      class MyClass{
      private static Resource res;
      static{ res = new Resource(); }
      
      //rest of code that uses the res reference  goes here
      }
      Are these two approaches completely identical, or would you favor one over the other for different reasons?

      Also is this third approach (nulling the reference before assigning a value to it) any different?
      class MyClass{
      private static Resource res = null;
      static{ res = new Resource(); }
      
      //rest of code that uses the res reference  goes here
      }
      The idea in every case is to have one reference to Resource for multiple instances of MyClass (assume thread safety is to be considered later) .. I know Singleton is another way to go (and want to avoid tactics like lazy instantiation), but a simple static reference like the above should also work, right?

      Many thanks.
        • 1. Re: static initializers
          3004
          Are these two approaches completely identical, or would you favor one over the other for different reasons?
          I would favor initializing at declaration when possible. It's simpler and cleaner. However, sometimes it's not possible, such as when initializing can throw a checked exception, or when you have to do more than just construct an object--e.g. if setting it's fields is a multistep process.

          >
          Also is this third approach (nulling the reference before assigning a value to it) any different?
          This is pointless, since it's given a value of null as a default before any of your code executes anyway.
          • 2. Re: static initializers
            807601
            I think you may have psyched yourself out with static blocks because there's nothing tricky about them. All three of your approaches are equivalent. The last one, where you explicitly set res to null is superfluous: static object fields are implicitly nulled out, to being with.

            Which should you use? Keep it simple (that's not a hard rule to remember!):
            private static Resource res = new Resource();
            Use a static initializer when you can't do this. For example your Resource constructor may throw an exception that you want to catch and log, then you may set res to something else.

            edit: we agree!
            • 3. Re: static initializers
              807601
              Hi jverd, thanks for your reply. Helpful advice as usual. Thanks to bidDaddy too.

              Just wondering these previous approaches, will ensure uniqueness of Resource across multiple instances of MyClass, correct?

              I want to ensure uniqueness first and then worry about thread safety.

              Thanks again
              • 4. Re: static initializers
                807601
                DeChristo wrote:
                Just wondering these previous approaches, will ensure uniqueness of Resource across multiple instances of MyClass, correct?

                I want to ensure uniqueness first and then worry about thread safety.
                1. static/static initializers give you the uniqueness you are looking for.
                2. thread safety? Before your MyClass constructor is called, the static fields/initializers have finished, unless you are doing something crazy like starting a thread there, or creating an instance of MyClass in Resource...
                • 5. Re: static initializers
                  807601
                  Question does that work for JFrames because I has a static JFrame that I only wanted one of but would multiples copies of the same window and actually had to hardcode the static instancing in. Or does something can when working with GUI...sorry to interrupt the OP's question (kind of rhetorical...answer if you want). I am confused...I do have that code too.
                  • 6. Re: static initializers
                    807601
                    No, I am not doing any other initializations or creating threads in the static blocks. I will go with the instantiation at the declaration level. Makes things easier and clearer.

                    The client/user class will be a totally different class, and threads will be started over there, like:
                    public class Client extends Thread{
                    MyClass base = new MyClass();
                    
                    public void run(){
                    //code that uses base reference goes here
                    //for every Client instantiation, there will be a new MyClass instantiation
                    //so every thread will act on a separate base reference
                    //but each base reference will share *a single* Resource reference
                     }
                    }
                    It crossed my mind to declare the base reference as static, (would there be any benefit to that? - based on this simple example) but that would be redundant, since I already have taken care of the uniqueness of the resource variable at a lower level (within MyClass class) -- Would you say this reasoning is right?

                    As for thread safety, back in the MyClass class, if the proper methods that access and modify the Resource variable are correctly synchronized, thread safety should be taken care of too. Right? I hope I am on the right path here.

                    Thanks again for the helpful advice.
                    • 7. Re: static initializers
                      807601
                      didittoday wrote:
                      Question does that work for JFrames because I has a static JFrame that I only wanted one of but would multiples copies of the same window and actually had to hardcode the static instancing in. Or does something can when working with GUI...sorry to interrupt the OP's question (kind of rhetorical...answer if you want). I am confused...I do have that code too.
                      With GUIs, you want to be mindful of the EDT and how you combine Swing with concurrency:
                      http://java.sun.com/docs/books/tutorial/uiswing/concurrency/index.html
                      • 8. Re: static initializers
                        807601
                        DeChristo wrote:
                        No, I am not doing any other initializations or creating threads in the static blocks. I will go with the instantiation at the declaration level. Makes things easier and clearer.

                        The client/user class will be a totally different class, and threads will be started over there, like:
                        public class Client extends Thread{
                        MyClass base = new MyClass();
                        
                        public void run(){
                        //code that uses base reference goes here
                        //for every Client instantiation, there will be a new MyClass instantiation
                        //so every thread will act on a separate base reference
                        //but each base reference will share *a single* Resource reference
                        }
                        }
                        It crossed my mind to declare the base reference as static, (would there be any benefit to that? - based on this simple example) but that would be redundant, since I already have taken care of the uniqueness of the resource variable at a lower level (within MyClass class) -- Would you say this reasoning is right?
                        The basic rule is: make a field static if it is logically wrong to have two instances of it.

                        >
                        As for thread safety, back in the MyClass class, if the proper methods that access and modify the Resource variable are correctly synchronized, thread safety should be taken care of too. Right? I hope I am on the right path here.
                        Since different MyClass objects are invoking Resource methods on a unique Resource object, class Resource sounds like it should be made to be thread safe, or you carefully synchronize access to it.
                        • 9. Re: static initializers
                          807601
                          Thanks, that makes sense. But if my only concern is the Resource, and Resource uniqueness and thread safe access are taken care of within MyClass (or Resource class itself is threadsafe), is there any point to having higher levels of static declarations?

                          I mean lets say that BiggerClient HAS-A BigClient which HAS-A Client, which in turn HAS-A MyClass that ultimately holds a static reference (HAS-A) to Resource.

                          Again, if we focus only on Resource, wouldn't be redundant to declare higher levels of static references? For example does it make sense to say BiggerClient HAS-A static reference to BigClient, which in turn HAS-A static reference to MyClass, etc..?

                          My understanding is that once I have uniquness of Resource at the lowest level, or at the levels that matters, all higher levels of static declarations shouldn't be required. I hope this is clear enough, sorry if I make things complicated, but would like to clear this up in my head.

                          Appreciate the help so far
                          • 10. Re: static initializers
                            807601
                            DeChristo wrote:
                            Thanks, that makes sense. But if my only concern is the Resource, and Resource uniqueness and thread safe access are taken care of within MyClass (or Resource class itself is threadsafe), is there any point to having higher levels of static declarations?

                            I mean lets say that BiggerClient HAS-A BigClient which HAS-A Client, which in turn HAS-A MyClass that ultimately holds a static reference (HAS-A) to Resource.

                            Again, if we focus only on Resource, wouldn't be redundant to declare higher levels of static references? For example does it make sense to say BiggerClient HAS-A static reference to BigClient, which in turn HAS-A static reference to MyClass, etc..?

                            My understanding is that once I have uniquness of Resource at the lowest level, or at the levels that matters, all higher levels of static declarations shouldn't be required. I hope this is clear enough, sorry if I make things complicated, but would like to clear this up in my head.

                            Appreciate the help so far
                            Don't use static to solve problem, real or perceived. Again, an object field is static if it is logically wrong in your design to create multiple instances of it.
                            • 11. Re: static initializers
                              807601
                              Thanks BigD, I think I might be panicking a bit too much over this. But what you said makes sense: It depends on the design.

                              thanks for the advice