Skip to main content

Are Java static initializers thread safe?



I'm using a static code block to initialize some controllers in a regsitry I have. My question is therefore, can I guarantee that this static code block will only absolutely be called once when the class is first loaded? I understand I cannot guarantee when this code block will be called, Im guessing its when the Classloader first loads it. I realize I could synchronize on the class in the static code block, but my guess is this is actually what happens anyway?





Simple code example would be;







class FooRegistry {



static {

//this code must only ever be called once

addController(new FooControllerImpl());

}



private static void addController(IFooController controller) {

// ...

}

}







or should I do this;







class FooRegistry {



static {

synchronized(FooRegistry.class) {

addController(new FooControllerImpl());

}

}



private static void addController(IFooController controller) {

// ...

}

}




Comments

  1. Yes, Java static initializers are thread safe (use your first option).

    However, if you want to ensure that the code is executed exactly once you need to make sure that the class is only loaded by a single class-loader. Static initialization is performed once per class-loader.

    ReplyDelete
  2. Yes, Static initializers are run only once. Read this for more information.

    ReplyDelete
  3. This is a trick you can use for lazy initialization

    class Singleton {
    static class SingletonHolder {
    static final Singleton INSTANCE = new Singleton();
    }
    public static Singleton instance() {
    return SingletonHolder.INSTANCE;
    }
    }


    As the static block in SingletonHolder will run once in a thread safe manner you don't need any other locking. The class SingletonHolder will only get loaded when you call instance()

    ReplyDelete
  4. Yes, sort of

    A static initializer only gets called once, so by that definition it's thread safe -- you'd need two or more invocations of the static initializer to even get thread contention.

    That said, static initializers are confusing in many other ways. There's really no specified order in which they're called. This gets really confusing if you have two classes whose static initializers depend on each other. And if you use a class but don't use what the static initializer will set up, you're not guaranteed the class loader will invoke the static initializer.

    Finally, keep in mind the objects you're synchronizing on. I realize this isn't really what you're asking, but make sure your question isn't really asking if you need to make addController() thread-safe.

    ReplyDelete
  5. In usual circumstances everything in the static initialiser happens-before everything that uses that class, so synchronisation is not usually necessary. However, the class is accessible to anything that the static intiailiser calls (including causing other static initialisers to be invoked).

    A class can be loaded by a class loaded but not necessarily initialised straight away. Of course, a class can be loaded by multiples instances of class loaders and thereby become multiple classes with the same name.

    ReplyDelete

Post a Comment

Popular posts from this blog

[韓日関係] 首相含む大幅な内閣改造の可能性…早ければ来月10日ごろ=韓国

div not scrolling properly with slimScroll plugin

I am using the slimScroll plugin for jQuery by Piotr Rochala Which is a great plugin for nice scrollbars on most browsers but I am stuck because I am using it for a chat box and whenever the user appends new text to the boxit does scroll using the .scrollTop() method however the plugin's scrollbar doesnt scroll with it and when the user wants to look though the chat history it will start scrolling from near the top. I have made a quick demo of my situation http://jsfiddle.net/DY9CT/2/ Does anyone know how to solve this problem?

Why does this javascript based printing cause Safari to refresh the page?

The page I am working on has a javascript function executed to print parts of the page. For some reason, printing in Safari, causes the window to somehow update. I say somehow, because it does not really refresh as in reload the page, but rather it starts the "rendering" of the page from start, i.e. scroll to top, flash animations start from 0, and so forth. The effect is reproduced by this fiddle: http://jsfiddle.net/fYmnB/ Clicking the print button and finishing or cancelling a print in Safari causes the screen to "go white" for a sec, which in my real website manifests itself as something "like" a reload. While running print button with, let's say, Firefox, just opens and closes the print dialogue without affecting the fiddle page in any way. Is there something with my way of calling the browsers print method that causes this, or how can it be explained - and preferably, avoided? P.S.: On my real site the same occurs with Chrome. In the ex