English 中文(简体)
Do I have to do a setSize() on a Vector before using it?
原标题:
  • 时间:2009-11-15 18:42:23
  •  标签:
  • java
  • java-me

Given

private final Vector v = new Vector();  //instance variable

the following 3 lines are in an instance method in the same class.

1.    int length = v.capacity();   
2.    int size = v.size();
3.    Object o = v.getElementAt(0);

I am getting an ArrayIndexOutOfBoundsException at line 3.

The debugger shows that the Vector has 10 elements.
length shows 10.
size shows 0.

Why is this exception being thrown, do I need to do a setSize() to use the Vector v?

最佳回答

The capacity() method tells you have many elements the Vector can take, before it has to increase its capacity. It doesn t tell you have many elements that currently is in the Vector, that s what size() is assigned to do. And in your case it does, since the Vector is empty.

You can specify the capacity by providing parameters to the constructor:

Vector v = new Vector(20);
/* This vector will have the starting capacity
   of 20 elements, before it has to increase
   its capacity */


Vector v = new Vector(10, 5);
/* This vector will have an initial capacity
   of 10 elements, and when it overflows the
   second parameter tells the vector to increase
   its capacity by 5. */

Edit

Based on your comments to other posts, it seems that you have two threads in your application - where one puts stuff into the vector and another one reads the vector?

Then you have to add a control structure to check wether the vector is empty or not, before trying to get elements from it.

Dirty example:

/* Vector instantiation goes here */

boolean keepRunningFlag = true;
while(keepRunningFlag) {
    if (!vector.isEmpty()) {
        Object o = vector.remove(vector.size() - 1);
        keepRunningFlag = doStuffWithVectorElement(o);
    }
}
问题回答

No, but you do have to add an element before you get it.

Vector is old school Java 1.0. It uses synchonrization as its default, which can affect your performance. Why are you not considering the newer java.util.List and java.util.ArrayList classes?

The capacity is the space allocated for current and future elements, an internal (to the vector) number which is exposed for performance reasons. The capacity is equal to or larger than the amount of elements it contains.

The size() shows you how many elements you put in the vector. The capacity is more in the nature of internal bookkeeping of the vector. You can only get elements 0... getSize() -1 out of the vector.

That said, if you don t use the data in multiple threads it s probably better to use ArrayList.

You can check whether the vector is empty by using isEmpty(), which should do something like getSize() == 0.

No. The vector has reserved space for 10 elements. But it doesn t yet contain any of those elements you need to add something to the vector using put

Length will tell you the amount of reserved space, size tells you how much you can actually use.

Vectors typically reserve more space than they need as an optimisation

As several people have mentioned, you don t want to look at the Vector s capacity, or (equivalently) the length of its internal array. In practice, you almost never want to look at the capacity of a Vector. You need to use size() (or isEmpty(), which returns true if and only if size() returns 0).

Attempting to call getElementAt(x) on an element that isn t there does not return null. It throws an exception.

Since you ve got another thread inserting elements, you probably want to check the size and retrieve the element atomically. Actually, it sounds like you re trying to implement a producer/consumer queue, in which case you want to also remove the element as part of the same atomic operation. The most straightforward way to do this is to synchronize on the Vector. eg:

Object o = null;
synchronized(v) {
    if (!v.isEmpty()) {
        o = v.getElementAt(0);
        v.removeElementAt(0);
    }
}
// at this point the first element of the vector will be removed
// (if there was one) and o be pointing at that first element. If
// the Vector was empty, o will still be null.

A few caveats with this code:

  • if v gets large, this becomes inefficient, because removing the first element in a Vector shifts all of the remaining elements over by one. If this is an issue for you you may want to find or write a queue class.
  • If a null is inserted in the Vector o will also be set to null. That may or may not be an issue for you.




相关问题
Spring Properties File

Hi have this j2ee web application developed using spring framework. I have a problem with rendering mnessages in nihongo characters from the properties file. I tried converting the file to ascii using ...

Logging a global ID in multiple components

I have a system which contains multiple applications connected together using JMS and Spring Integration. Messages get sent along a chain of applications. [App A] -> [App B] -> [App C] We set a ...

Java Library Size

If I m given two Java Libraries in Jar format, 1 having no bells and whistles, and the other having lots of them that will mostly go unused.... my question is: How will the larger, mostly unused ...

How to get the Array Class for a given Class in Java?

I have a Class variable that holds a certain type and I need to get a variable that holds the corresponding array class. The best I could come up with is this: Class arrayOfFooClass = java.lang....

SQLite , Derby vs file system

I m working on a Java desktop application that reads and writes from/to different files. I think a better solution would be to replace the file system by a SQLite database. How hard is it to migrate ...

热门标签