Question

Applets and static variables.

Asked by: omry_y

Concider a big and complicated applet.
I need alot of information available throughout my applet, without having to pass a reference to it.
therefor, use the singleton pattern extensively.
the problem is, that when I open my applet in two different pages, in some cases (I can duplicate it), problems that are related to the static variables I use show up.
such problems are caused because the static variable of one applet gets overwritten by the static variables of the other.

any advices will be welcomed (except re-design :-)

heyhey, please participate.

This Question has been solved and asker verified All Experts Exchange premium technology solutions are available to subscription members.

Subscribe now for full access to Experts Exchange and get

Instant Access to this Solution

  • Plus...
  • 30 Day FREE access, no risk, no obligation
  • Collaborate with the world's top tech experts
  • Unlimited access to our exclusive solution database
  • Never be left without tech help again

Subscribe Now

Asked On
2000-10-10 at 04:48:58ID11506138
Tags

applet

Topics

Java Programming Language

,

Java Standard Edition

,

New to Java Programming

Participating Experts
8
Points
256
Comments
34

Trusted by hundreds of thousands everyday for fast, accurate and reliable tech support.

  • "The time we save is the biggest benefit of Experts Exchange to Warner Bros. What could take multiple guys 2 hours or more each to find is accessed in around 15 minutes on Experts Exchange." Mike Kapnisakis, Warner Bros.
  • "Our team likes having a resource that is more secure than just using Google and most experts using this service really know their stuff. It's nice to look here first versus using Google." Dayna Sellner, Lockheed Martin
  • "Anytime that I've been stumped with a problem, 9 out of 10 times Experts Exchange has either the accepted solution or an open discussion of the potential solution to the problem." Kenny Red, eBay Inc.

See what Experts Exchange can do for you.

Got a question?

We've got the answer.

Experts Exchange has been collecting answers to technology questions since 1996…3 million and counting! If you have a question, chances are we already have your answer.

Screenshot of Experts Exchange Knowledgebase

Need individual assistance?

Our experts are ready to help.

If you can't find the exact answer you're looking for, ask our exclusive community of 50,000 experts. You’ll get a personalized answer from a trusted professional.

Screenshot of Experts Exchange Knowledgebase

Want to learn from the best?

Read articles from industry experts.

Thousands of free tech tips, tricks, how-to’s and tutorials are available in our peer reviewed articles section. See for yourself how smart our experts are, no login required.

Screenshot of an Article

Working on a long term project?

Store your work and research.

Save solutions to your questions, answers you’ve discovered through searching plus helpful articles in your personal knowledgebase for easy future access.

Screenshot of Experts Exchange Knowledgebase

Access the answers to your technology questions today.

Subscribe Now

30-day free trial. Register in 60 seconds.

What Makes Experts Exchange Unique?

Members of the expert community talk about why the experience at Experts Exchange is different than what you will find anywhere else.

Trusted by the world's most respected brands.

image of each brand's logo

Faithfully serving IT professionals since 1996.

Experts Exchange Logo

Try it out and discover for yourself.

Subscribe Now

30-day free trial. Register in 60 seconds.

Related Solutions

  1. To heyhey
    Hi, heyhey_ This is towards " ABout Error NoClassDefFoundError " You said >you have to install Java Plug-In on your computer. >NC is 1.1 compatible and javax.swing.JApplet exist in JDK1.2. >Java Plug-In will make your browser 1.2 compatible. After I...
  2. Singletons and Garbage collection.
    I've heard that a singleton in java may be garbage collected. To get around this you are supposed to put a sleeping thread in it, so that it won't be collected. First of all, is this true? Anyway, I wrote some code to test this, it uses finalize to tell when the garbage coll...

Free Tech Articles

  1. WARNING: 5 Reasons why you should NEVER fix a computer for free.
    It is in our nature to love the puzzle. We are obsessed. The lot of us. We love puzzles. We love the challenge. We thrive on finding the answer. We hate disarray. It bothers us deep in our soul. W...
  2. SCCM OSD Basic troubleshooting
    SCCM 2007 OSD is a fantastic way to deploy operating systems, however, like most things SCCM issues can sometimes be difficult to resolve due to the sheer volume of logs to sift through and the dispe...
  3. Migrate Small Business Server 2003 to Exchange 2010 and Windows 2008 R2
    This guide is intended to provide step by step instructions on how to migrate from Small Business Server 2003 to Windows 2008 R2 with Exchange 2010. For this migration to work you will need the fo...
  4. Create a Win7 Gadget
    This article shows you how to create a simple "Gadget" -- a sort of mini-application supported by Windows 7 and Vista. Gadgets can be dropped anywhere on the desktop to provide instant information, ...
  5. Outlook continually prompting for username and password
    There have been a lot of questions recently regarding Outlook prompting for a username and password whilst using Exchange 2007. There are a few reasons why this would happen and I will try to cover t...
  6. Backup Exchange 2010 Information Store using Windows Backup
    There seems to be quite a lot of confusion around the ability to backup Exchange 2010 using the built in Windows Backup feature. This stems from the omission of this feature prior to Exchange 2007 s...

Cloud Class Webinars

  1. Avoiding Bugs in Microsoft Access
    Alison Balter takes and in-depth look at avoiding bugs in Access. In this webinar you will learn about using the immediate window to debug your applications, invoking the debugger, using breakpoints to troubleshoot, stepping through code, setting the next statement to execute, ...
  2. Top 10 Best New Features in Visio 2010
    Scott Helmers gives live demonstrations of the top 10 new features in Visio 2010. This webinar will teach you how to create compelling diagrams by adding shapes to the page with a single click, linking the shapes in a diagram to data in Excel (or SQL Server, or SharePoint), ...
  3. IT Consultant Business Secrets Revealed
    Michael Munger, Experts Exchange tech pro and IT consultant, pulls back the curtain on his very successful businesses and answers question on every IT consultant and business owner should know about. He shares secrets on what he did to solve the 5 most common problems in IT, ...
  4. Disaster Recovery and Business Continuity
    Quest CTO, Mike Billon, gives an overview of the steps involved in building a dunamic disaster recovery plan. Through case studies and an examination of software/hardware tooles for monitoring and testing, you'll gain a better understandin of where you are, where you want ...
  5. Organize Your Visio Diagrams with Containers and Lists
    Scott Helmers uses cross functional flowcharts, wireframe diagrams, data graphic legends and seating charts to teach you: how to ustilize all three new structured diagram components in Visio 2010, the best practices for organizeing shapes in previous version of Visio, how to organize ...
  6. How to Us Objects, Properties, Events and Methods in Microsoft Access
    Alison Dalter gives an in-depbth look at objects, properties, events and methods in Microsoft Access. In this webinar you will learn about using the object browser, referring to objects, working with properties and methods, working with object variables, understanding the ...

Join the Community

Give a Little. Get a Lot.

Join the community of experts here and help other tech pros by answering question in your area of expertise. You can earn FREE access to all Experts Exchange's premium features and resources.

Join the Community

Answers

 

by: CEHJPosted on 2000-10-10 at 05:25:32ID: 4653955

Can you be specific about what the problems are?

 

by: jituPosted on 2000-10-10 at 06:10:56ID: 4654847

Omry...your question is not clear. I don't understand what you exactly need. From what I have understood....you are having static classes in an applet and you are trying to access them thru' the same machine.
   Why should they be static at the first place? Static has to be used only when you are going to run the app from 2 different machines. Only then they are going to be local to the machine. If due to unavoidable reasons you have to keep them static then I would suggest use getXXX() and setXXX() methods. Depending on the condition overwrite them.

 

by: Sasha_MapaPosted on 2000-10-10 at 06:36:27ID: 4655095

listening...

Sasha Maryanovsky.

 

by: CEHJPosted on 2000-10-10 at 07:42:33ID: 4656007

Omry, you seem to be doing what I have to check myself from doing quite often - pre-diagnosing the problem. Can you say what the actual symptoms are before we get into the causes? What's happening, are you seeing unexpected results? What are the details.

 

by: mchermPosted on 2000-10-10 at 08:22:49ID: 4656604

omry_y:

I'm not surprised that (to use your words): "the static variable of one applet gets overwritten by the static variables of the other". At least not if "one applet" and "the other" refer to two different instances of the same class.

If my understanding is correct, then this is not surprising, it is simply the way that static variables work... they are shared among all instances of the class. That includes the same applet appearing on different pages.

So I'm going to do just what you asked that we NOT do, and suggest a re-design. But I'm hoping that it's not going to be too BIG a redesign.

If I understand correctly, your problem is that you want to have access to certain information all over the place, and don't want to have to pass it around everywhere (a good point), or copy it (which could be avoided other ways, but see point #1). So you used static variables and methods... java's closest equivalent to "global variables". But you DON'T want the information to be global across EVERYWHERE, just global to the particular applet instance (ie, the applet on THIS page, not shared with the one on some other page).

So here's what I recomend in the way of a re-write. First of all (and you may already be doing this, I'm not sure), don't deal with each individual variable separately, group them all into a big "globals" object. This way, if you want to change how it's accessed, you'll just have one place to change. So instead of having Widget.foo, and Widget.bar, and Fidget.foobar as separate variables, you have a class called Globals, and an instance called "global", so that the access is Globals.global.foo, Globals.global.bar, and Globals.global.foobar. I might even go one step farther, and write an accessor METHOD for getting Globals.global. So now your accessers in your code would look like this: Globals.get().foo, Globals.get().bar, Globals.get().foobar.

Now that you've done this, all other changes will be easy. In fact, you may even be able to get away with changing nothing but the method Globals.get(). I would say that the next step is to consider just how "global" you want each variable to be. Each variable might be truely UNIVERSAL (across all applets), or global only within a single instance of the applet. There might even be ones which needed to be global across all users of the applet (in which case you need to coordinate with the server). I'm going to assume that you decide that all of your variables need to be global to the particular instance of the applet (the onee on this page), but no broader.

Now that we've decided how broad to make it, things are basically laid out for us. If we had decided to make things global across all applets, we'd make globals be a static variable (ie, Gloabals.get() would read as follows):

    class Globals {
        static Globals globals;
        public static Globals get() {
            return globals;
        };
    }

But that wasn't our decision... we wanted it to be specific to an instance of the Applet. So that's where we put it.

    class MyApplet extends Applet {
        Globals globals;
        init() {
            globals = new Globals(init here);
        }
    }

Now when writing code in the applet, we can access the "globals" as this.globals.foo, this.globals.bar, and this.globals.foobar. Or, instead, we can re-write Globals.get() to handle it for us, adding applet as an extra parameter:

    class Globals {
        public static get(MyApplet applet) {
            return applet.globals;
        }
    }

And this is how I'd probably do it. But I'm guessing that you're looking at this and saying "But I really DON'T want to pass 'applet' around everywhere!". If I were you, I'd stop here. But if you really want to avoid passing applet around everywhere, there IS a solution... make the variables global to the THREAD. (This is more-or-less equivalent to making them global to the applet, but not quite.) If you're really interested in seeing this solution, let me know and I'll add it.

-- Michael Chermside

 

by: Sasha_MapaPosted on 2000-10-10 at 08:32:39ID: 4656800

Sorry to burst into the discussion like this, but Omry and I work together and he's AFK right now, so I though I'd respond for him :-) I hope he doesn't mind...

CEHJ: Omry is quite clear on what is going on and why - he is looking for a way around the proble, he's not looking into understanding the problem - he already understands it. There are no unexpected results, just ones that differ from desirable :-)

mcherm: Hehe, I think you have thought of almost all the solutions we have thought about - unfortunately, most of the "action" happens in the AWT thread, which is shared between the applets (there's just one per JVM) - so making the data global to a thread will essentially make it global to all the classes that perform their duties in the AWT thread :-)

Sasha Maryanovsky.

 

by: ET3DPosted on 2000-10-10 at 09:51:14ID: 4658150

How about a redesign? :)

You need something to determine which of the applets you're in. Depending on your UI, you could try to go up the AWT tree using getParent(), until you get to the applet, and then access data there. For example:

class App extends Applet {
  Globals myGlobals;
  Globals getGlobals(Component inComponent) {
     Container parent = inComponent.getParent();
     if (parent instanceof Applet)
       return ((Applet)parent).myGlobals;
     else
       return getGlobals(parent);
  }
  ...
}

If the Applet isn't the parent (or ancestor) of the components, you can implement a similar method in your Window class, and pass a reference to the globals to its constructor, that it'll keep.

Nice number of points, BTW.

 

by: ET3DPosted on 2000-10-10 at 09:52:50ID: 4658166

Oops, forgot 'static' for 'getGlobals'.

 

by: omry_yPosted on 2000-10-10 at 09:54:29ID: 4658179

mchem : as Sasha stated, we already thought about all of these solutions.

nice thinking.

you are right, since I dont want to pass the applet around, or any other key.

it all boils down to the need to have a static variable (the real info, or a key to the real info) that will be global to the applet that declare it.

 

by: omry_yPosted on 2000-10-10 at 10:00:47ID: 4658238

CEHJ : with all the respect, bealive me you dont want to dive into details.
I have the problem diagnosed and I clearly understand when it happens, and why.
what I need is a good alternative, or a magical way to achive it without re-designing.

 

by: omry_yPosted on 2000-10-10 at 10:10:59ID: 4658375

ET3D : nice idea.
i`ll try it and get back to you.

btw : I have more then one applet in my hirarchy, but lets leave it out of it :-)

 

by: Sasha_MapaPosted on 2000-10-10 at 10:20:09ID: 4658542

Excellent idea ET3D - use the applet or the applet frame as the key... :-)

Sasha Maryanovsky.

 

by: ravindra76Posted on 2000-10-10 at 11:16:50ID: 4659279

One of the good questions in EE

:)

 

by: mchermPosted on 2000-10-10 at 11:38:25ID: 4659599

omry_y & sasha_mapa:

Ouch. So if the thread trick won't work, we're in trouble. The fundamental issue is to have SOME key which identifies which instance of the applet we are in. If we had anything -- even just an "applet ID #" -- available everywhere, we could use that as a key to a Hashmap of Global objects, which would solve the problem. The shared nature of the event handler thread kinda blows away using threads to identify it, as long as your work is done in the AWT thread. ET3D's idea of using Component.getParent() to drill your way up the component hierarchy to the applet is a good solution as long as you are doing work somewhere where a Component is available, but in general, the code may be executing in arbitrary objects. I'm really beginning to think that you'll have to stoop to passing SOMETHING around, even if it's only a token which is key to a Hashmap.

The fundamental problem, as we've stated it, is for code executing in an arbitrary method of an arbitrary object to figure out which applet it is part of. We have stipulated that it cannot determine it by examining any method parameters. Since the object it is part of is arbitrary, we cannot determine it by examining any instance variables (ET3D's solution relies on the object not being arbitrary). We cannot determine it by examining any static variables of any class, because those would be the same regardless of which applet was being displayed. We cannot determine it by examining the thread we are executing in because that is the AWT-event thread regardless of which applet it is. We cannot determine it by somehow interacting with the page, because to do that would require that we have access to the Applet object which begs the question. We cannot determine it by connecting to the server because the server has no way to identify us. I'm running out of possibilities here! I think if you massage the above paragraph you wind up with an information-theoretic proof that it's IMPOSSIBLE to solve the problem as stated.

So I'd say, go outside the bounds of what was defined. Either try to enforce a solution like ET3D's, which works in "a lot" of cases, or go ahead and pass around something... the Applet object would be one choice, but it could be an arbitrary token you create... it's the same amount of copying (1 pointer) either way.

An interesting issue. Besides this case (the "lazy" programmer who is just trying to avoid passing variables all over the place) this same issue comes up when trying to develop a generalized logging or debugging support class for java. I have developed such things before, and my solution has been to use static accessors (your original solution) with OPTIONAL parameters specifying which [whatever it is -- applet in your case] is "active". For instance, in a logging system, I allowed the calling class to pass itself in so the logger could determine what class generated the log message. If this parameter was ommitted, then the "logging-class" column was left blank in the logging output. Other optional parameters allowed the calling code to specify things like the "user-id" and the "user-session" IF they happened to be available. If no optional parameters were supplied then the logger logged little more than the thread it originated from, the time of the logged event, and the log error message (which was NOT optional!).

-- Michael Chermside

 

by: heyhey_Posted on 2000-10-10 at 12:09:16ID: 4660150

> heyhey, please participate.

the way I do it (sorry - I haven't read the whole discussion)

0. wrap all the specific data in some Configuration object
you can
1. associate Configuration object per Thread
2. associate Configuration object per component
3. pass your Configuration object to all the objects that need it (as constructor parameter for example)

3. is the most universal. 1. is suitable for server side enviroment and allows you some additional flexibility (like keeping a stack of Log objects per Thread). 2. may be the easiest way to solve the problem if you work with GUI objects only.

I've been always LAZY programmer, so I HATE solution 1. but it seems to be the BEST choice in the log run

my 0.02$ :)

 

by: omry_yPosted on 2000-10-10 at 12:24:10ID: 4660423

"the way I do it (sorry - I haven't read the whole discussion) "

you should, its an interesting one, and not too long.

1 is not good enough, since the action accures in the AWT event thread, and there is one and only one of these.

2 is, in a way, the suggested solution.

about 3, I dont feel like rewriting so much, so that was only a last resort.


10x for your participation! :-)

 

by: heyhey_Posted on 2000-10-10 at 12:38:31ID: 4660771

I've just reserved a seat to see which answer you are going to accept. :) don't have time to discuss right now ...

btw. 3 is the most universal one.

P.S. 3. is suitable for server side apps (servlets too). 2. is good ONLY if you work with visual objects ONLY (which I personally never do)

but you know better your requirements after all.

 

by: ET3DPosted on 2000-10-10 at 12:51:04ID: 4661019

mcherm, It may be true that there's no solution for arbitrary objects, but considering that methods called from AWT usually have access to a component, and that methods not called from AWT run in their own thread, this can pretty much cover most bases.

There's even a solution for objects that are called in the AWT thread but aren't components, if they are from top level classes (that extend Object). In that case, have them extend some base class of yours, that will contain the reference, and will take it from the thread in its constructor (or will keep a reference to the Thread where it was created).

 

by: omry_yPosted on 2000-10-10 at 12:51:31ID: 4661023

I can compine 2 and 3.
for most cases, I need the global info in components, but if I need it in an object that is not a component, I can just pass it to it in one of the old fasioned ways.

 

by: mchermPosted on 2000-10-10 at 13:50:54ID: 4662399

omry_y:

I agree... this sounds like the right approach. Basically, use Component as ET3D suggests, and this will cover most of the cases. Then pass something (how about a component!) to all the other cases.

-- Michael Chermside

 

by: omry_yPosted on 2000-10-11 at 04:42:28ID: 4672378

ET3D :  I am trying to do it now, and already I see a major drawback in the approach :
before attempting to get a configuration object, the chain of panels have to be complete, i.e : every panel should have a parent.

this means that I cant access the configuration object in the constructor of the specific panel, because a panel can only have a parent after it was constructed,


a workaround would be to move the contrutor code to addNoify(), and to make sure the constructor code gets called only once, but this introduce global change to the source, which I try to avoid.

if I am forced to make such a change, I`d rather it to be change to pass the configuration object up the chain instead of something so hacky as move the contructor to the addNotify().

well guys, look like we have to go back to the blue board :-)





 

by: ET3DPosted on 2000-10-11 at 06:40:11ID: 4674979

I think that it will work fine if you combine the thread and getParent methods. You construct the panel in the applet thread, so you have no problem accessing that. In the AWT thread, you have already constructed everything, so you can use the getParent method.

It's a bit of extra work to implement both, but as I said before, these two together cover most bases.

 

by: mchermPosted on 2000-10-11 at 06:54:42ID: 4675457

Wow. What a lot of work for what seems like it would be such a simple thing. Shows, I guess, that's it's not so simple after all. My strongest recomendation is that, whatever you wind up doing, you hide it all in a single method (and/or a single object passed around) because you definately don't want this cluttering up your application logic.

-- Michael Chermside

 

by: bazarnyPosted on 2000-10-11 at 08:12:58ID: 4676479

Ugh, such a long discussion...

Did anyone suggested separate classloader for each applet? (I guess it won't work for 1.1 JVM though).

Starting applet class does nothing except of creating worker class through newly created URLClassLoader. It's 1.2 specific class and I doubt that 1.1 security will allow use of class loader, if security is not an issue, it's still possible to create custom class loader similar to URLClassloader. Each applet instance will get own set of classes and static variables.

Regards,
Igor Bazarny

 

by: omry_yPosted on 2000-10-11 at 08:51:57ID: 4677630

You cant replace the classloader in applets, not even in a signed applet.
(it may somehow work in explorer, but never in netscape).

 

by: heyhey_Posted on 2000-10-11 at 10:58:19ID: 4680443

when exactly do you create your objects and when exactly do you need configuration information ?

 

by: omry_yPosted on 2000-10-11 at 10:59:39ID: 4680454

Excellent idea.

mcherm, you have some points waiting for you for your participation.

 

by: omry_yPosted on 2000-10-11 at 11:17:34ID: 4680760

just to make it clear :
the Excellent idea was aimed at ET3D :-)

 

by: ET3DPosted on 2000-10-11 at 11:40:12ID: 4681266

I'm happy that I can offer some help to such Java experts as yourself and Sasha. You seem to be working on something pretty interesting. This and Sasha's question about resolution were pretty thought provoking, compared to other questions on this site.

 

by: omry_yPosted on 2000-10-11 at 11:56:37ID: 4681664

I really wasnt very optimistic when I posted the question..
I was pretty sure I cant be solved in a clean way.
Glad I was wrong.

 

by: omry_yPosted on 2000-10-11 at 12:18:47ID: 4682059

heyhey :
I create in my applet init, and I need most of the info in panels that are created in this init.
thats why thread associating covered most of the cases.

in most of the other cases, I neeeded the info in Components, at the awt thread (action, handleEvent, and stuff like that).
thats where Component association was useful.

the rest of the cases are Objects that are not subclasses of Component, thus, have no parent, and may be used in any thread context, thats where I used the standard way to pass parameters - aka constructor argument.

it wasnt a big pain, because these object were created close to points where I coulds get the configuration in one of the other two ways.

in general, my implemenation looks like



public class blah
{

      private static Hashtable configurations = new Hashtable();
      public blah()
      {
            //..
            Configuration config = new Configuration(/*...*/);
            configurations.put(Thread.currentThread(),config);
            //..
      }

        public static Configuration getConfiguration(Thread t)
        {
                return (Configuration)configurations.get(t);
        }

        public static Configuration getConfiguration(Component c)
        {
                return getMapGUI(c).config;
        }

        private static blah getMapGUI(Component c)
        {
                if(c instanceof blah) return ((blah)c);
                else
                {
                        if(c.getParent() == null)
                        {
                                throw new IllegalArgumentException("Component does not have a parent.");
                        }

                        Container parent = c.getParent();
                        while(parent != null)
                        {
                                if(parent instanceof blah) return ((blah)parent);
                                else
                                        parent = parent.getParent();
                        }

                        return null;
                }
        }

}


where I choose which getConfiguration method to call acordint to the context.

20120131-EE-VQP-002

3 Ways to Join

30-Day Free Trial

The Experts

98% positive feedback on 31,087 answers since March 2000. angeliii is a Microsoft Most Valuable Professional for his work with MS SQL Server & Develoment.

He has also proven his knowledge of Visual Basic Programming, PHP Scripting and Oracle Databases.

The Experts

97% positive feedback on 10,752 answers since July 2000. lrmoore has more than 18 years experience in the networking industry.

The six-time Mircosoft MVPs specialties include firewalls, virtual private networking, and network management.

Testimonials

"...and excellent source for support... Kind of like having your very own IT dept." Electriciansnet

Testimonials

"I was apprehensive at signing up at first. However... it has already made my life as an IT administrator much easier." JaCrews

Testimonials

"WOW! You guys have great, active, and knowledgeable people on here." moore50

Business Clients

Business Clients

In the Press

"If you’ve got a question... Experts Exchange can supply an answer.”

In the Press

"...an invaluable aid for both IT professionals and those who require tech support."

In the Press

"where IT professionals provide quick answers on just about any topic"

Business Account Plans

Loading Advertisement...