Public Group

# interesting problem

This topic is 4854 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

I am using javac to compile an applet and am getting some interesting error messages. Most importantly, the compiler doesn't seem to be able to see variables declared in my init() function. Any controls (JCheckbox, JPanel, JButton, etc.) declared in init() show up as "can't find symbol" errors in my listeners. For example in my itemStateChanged listener (listens for ItemEvent events sent by JCheckbox instances): void itemStateChanged(ItemEvent ie) { Object source = ie.getSource(); if(source == checkbox_1) // checkbox_1 defined perfectly in init() { /* blah */ } else if(source == checkbox_2) { /* blah */ } .... } How are these variables falling out of scope? I am pretty much following the examples in my Java book verbatum, except my program is a leedle more complex. I also declare arrays of application-defined class objects in my program. Naturally then, I would like to iterate these arrays. The problem is I have to declare them with an unknown size because I don't know how many will be needed at runtime: Widget[] w; int i; for(i = 0; i < w.length; w++) { /* blah */ } javac is screaming at me that it cannot find the .length symbol? WTF? And last but not least, I am trying to iterate a LinkedList. Here is my code: LinkedList list = new LinkedList(); ListIterator iter = new ListIterator(); iter = list.listIterator; Pretty standard, right? But javac is complaining that 'iter' is abstract and cannot be instantiated????? WTF?? Why would java build an object like a ListIterator as an abstract data type?

##### Share on other sites
Quote:
 Original post by hisDudenessvoid itemStateChanged(ItemEvent ie){Object source = ie.getSource();if(source == checkbox_1) // checkbox_1 defined perfectly in init(){ /* blah */ }else if(source == checkbox_2){ /* blah */ }....}

This depends on where you declared these items. If you declared them locally in your init() method, like
void int( ) {
CheckBox checkbox_1;
...
}
the variable will be out-of-scope outside the init() method. You would need to declare them as class members to access them outside the init() method.
Quote:
 LinkedList list = new LinkedList();ListIterator iter = new ListIterator();iter = list.listIterator;Pretty standard, right? But javac is complaining that 'iter' is abstract and cannot be instantiated????? WTF?? Why would java build an object like a ListIterator as an abstract data type?

[smile]
The iterator is abstract as it's just a common interface for all types of lists. You should not instanciate it, but instead assign it to the one returned by your list instance:
ListIterator iter = list.listIterator;

As for the array-problem - my Java is a bit rusty, but isn't "length" a method rather than an attribute (e.g. w.length() instead of w.length)?

HTH,
Pat

##### Share on other sites
1. Definitions go out of scope as soon as the scope ends. You cannot access definition that are in another (separate) scope. Concrete example: you cannot access objects defined in another function.
Quote:
 This depends on where you declared these items.

Nitpicking: you mean defined.

2. You must allocate an array before you can use it. This way Java has no clue about the length of your array either.
Quote:
 As for the array-problem - my Java is a bit rusty, but isn't "length" a method rather than an attribute (e.g. w.length() instead of w.length)?

No it's an attribute. String has a method length() though.

3. LinkedList.listIterator is a function which you must call with a parameter.
Quote:
 The iterator is abstract as it's just a common interface for all types of lists. You should not instanciate it, but instead assign it to the one returned by your list instance:LinkedList list = new LinkedList();ListIterator iter = list.listIterator;

Actually the right syntax is:
ListIterator iter = list.listIterator();

In general these errors are so basic that I suggest you first get yourself a book teaching Java or try some tutorials online.

Illco

##### Share on other sites

1. You say that the variables declarted & defined in init() go out of scope at the end of init(). However ALL the examples in my introductory Java programming book (which you suggested I get) show controls being declared and defined in init() and then used elsewhere in various listener functions....

Even if you're right, if all I am using init() for is to create variables, should I just omit the function completely and declare them as my applet's class members?

2. As for the arrays, Java must provide a mechanism for dynamically allocating arrays of unknown size at runtime. My program absolutely depends on this. Well, to be more accurate, I have a class - Widget - and depending on user input, the program generates an unknown number of instances of Widgets. So how do I (using arrays or otherwise) iterate through this collection of an indefinite number of Widgets. There must be SOME way to do this.

hisDudeness

##### Share on other sites
Quote:
 1. You say that the variables declarted & defined in init() go out of scope at the end of init(). However ALL the examples in my introductory Java programming book (which you suggested I get) show controls being declared and defined in init() and then used elsewhere in various listener functions....

That is impossible. But I think I can see what it is they are doing. They probably declare the variables as members of the main applet class, then initialize them in the init() method and subsequently use them in other members. See this example:
class MyApplet{  // Declare the variables  JButton jButton;  JLabel jLabel;  /**   * Init method. Initializes the controls.   */  void init()  {    // Initialize the controls    jButton = new JButton( "Press here" );    jLabel = new JLabel( "A label" );  }  /**   * Change the buttons text.   */  void doSomething()  {    jButton.setText( "Press here again" );  }};

Quote:
 2. As for the arrays, Java must provide a mechanism for dynamically allocating arrays of unknown size at runtime.

This is of course possible. You can use the new operator to generate these. See this example:
class MyApplet{  // Declare room for the widgets  Widget[] widgets;  /**   * Initializes the widgets.   */  void init()  {    // Now I don't know where your's come from but as an example assume    // we make six widgets.    widgets = new Widget[6];  }  /**   * Do something with the widgets.   */  void doSomething()  {    for ( int i = 0; i < widgets.length; i++ )      widgets.widgetMethod();  }}

I hope this clarifies some of your problems. If not feel free to post again; at least you want to learn something which I appreciate.

Illco

hisDudeness[/quote]

##### Share on other sites
beautiful - thanks for the help guys

##### Share on other sites
actually Illco - thats not all....I have a tendency to lie.

I have two classes called Widget and Foo. In my Widget class definition, I have an array of Foo objects...

The problem is that I don't know how much Foo objects I will need at runtime. The user may specify 3....or 300.

How can I circumvent this? Perhaps asking the user for how many Foo objects they want, and then passing that number into the Widget constructor??

class Widget
{
int x,y,z;
Foo[] f;

Widget(int a, int b, int c, int numFoo)
{
x = a;
y = b;
z = c;

int i;
for(i = 0; i < numFoo; i++)
{
f.fooData1 = blah;
f.fooData2 = moreBlah;
}
}

Is this a good approach or do you have any better suggestions?

##### Share on other sites
Look at this thread (especially the last post)
http://www.gamedev.net/community/forums/topic.asp?topic_id=361512
on a similar problem of using fixed / dynamic arrays. With a dynamic array you'll be able to expand the array on demand.

Please notice that the solution you've posted above misses a
this.f = new Foo[numFoo];
and hence will die with a NullPointerException!

It should be
class Widget{  int x,y,z;  Foo[] f;   Widget(int a, int b, int c, int numFoo)  {    x = a;    y = b;    z = c;     this.f = new Foo[numFoo];    int i;    for(i = 0; i < numFoo; i++)    {      f = new Foo();      f.fooData1 = blah;      f.fooData2 = moreBlah;    }  }}

EDIT: At what time do you know how many Foos to allocate? If another demand pops up from time to time, then a dynamic array is absolutely suitable. If the total amount is fixed you could use a dynamic but also a fixed array, of course. If the amount is furthurmore known at the time of creating the Widget object than your solution above is ok.

EDIT2: I've forgoten that also the array members have to be allocated...

[Edited by - haegarr on December 2, 2005 3:51:21 PM]

##### Share on other sites
Yeah what ^^ he ^^ said.

##### Share on other sites
haegarr,

The statement: this.f = new Foo[numFoo]; <-- Is the 'this' keyword mandatory, or is it just good practice? I thought that when you reference data members from within a class that 'this' was just redundant. If I am wrong then perhaps you could explain it for me?

Also - YES YES YES!!! I would indeed like my class arrays to be dynamic. I am not constrained to any paradigm here - if you feel an ArrayList would be more suitable to do the job than I am all ears.

Nevertheless, sticking with dynamic arrays for the time being, I am still having trouble understanding how to use new to dynamically allocate here:

// one of these days I'll expend the energy and look up how to use the
// quote tag on these forums :-)
class Widget
{
int x;
Foo[] f;

Widget(int num)
{
x = num;
this.f = new Foo[ .....and here is where I'm lost ];
int i;
for(i = 0; i < HMMMMM....?; i++)
{
f.blah = sayWhat;
f.blah2 = omgThatIsInsane;
// etc.
}
}
}

• ### What is your GameDev Story?

In 2019 we are celebrating 20 years of GameDev.net! Share your GameDev Story with us.

• 18
• 12
• 12
• 11
• 9
• ### Forum Statistics

• Total Topics
634753
• Total Posts
3019146
×