Java Data structures

Well yes, LinkedHashMap has a special constructor which allows the ‘move-the-last-accessed-entry-to-the-front’ behaviour which Riven described, which you use for implementing a simple LRU.
Look at LinkedHashMap.Entry.recordAccess() where this is implemented.
I don’t think this sort of behaviour exists in a normal HashMap.

sproingi, that advice is right, exept for ArrayLists imo.
You often need ArrayList.trimToSize(), which trims the array to it’s size. For example if you have a method putting (not-knowing how much) elements into an ArrayList, and then never or not often changes it again, you could use .trimToSize() to reduce memory usage.

I think my advice is right 99% of the time for ArrayLists too, but obviously if you need the functionality of a specific type, you use the specific type. If you’re never going to change the size of an ArrayList, then you should set the size in the constructor and it will only allocate that many elements.

In fact the advice gets even more general for methods. If you have a method that takes an ArrayList and does nothing but loop over it, it should take an Iterable instead. I don’t get that abstract with publicly-readable fields for obvious reasons though.

Consider the following scenario:

You have a directory and you want to search all the files inside them recursively, and add then to an ArrayList.
You can’t set the size in the constructor, since you don’t know the size.
You can only trim it to size after you have found all the Files.

The thing you could do is return a simple List of Files in the end after you got all the Files… Little src code to make it clear:


public static List<File> getFilesFromDir(File directory) {
    // Check for "directory" being a directory:
    if (!directory.isDirectory()) {
        throw new IllegalArgumentException(directory.isDirectory() == false);
    }
    // Create new ArrayList, keep it as ArrayList, to call .trimToSize(); later:
    ArrayList<File> files = new ArrayList<File>();
    // Add the files recursively:
    getFilesRecursive(directory, files);
    files.trimToSize();
    return files;
}

private static void getFilesRecursive(File dir, ArrayList<File> list) {
    // For each File in the directory "dir":
    for (File file : dir.listFiles()) {
        // If it's a Directory, call this method with the File "file" as directory:
        if (file.isDirectory()) {
            getFilesRecursive(file, list);
        } else { // Else add it to found files, since it is a file, not directory:
            list.add(file);
        }
    }
}

(fast-typed, not syntax-tested)

Sure, using the ArrayList implementation internally in the local and returning the abstract List is 100% legit. It’s hard to boil that down to one-liner advice of course, but those declarations are also perfectly good field declarations too.

you could do something like this : :smiley:


public List<Foo> get() {
    // Create ArrayList, and internally keep it as ArrayList
    ArrayList<Foo> list = new ArrayList<Foo>();
    // Do stuff with the ArrayList
    //...
    // return it as List<Foo>!
    return list;
}

What about Vector http://docs.oracle.com/javase/1.4.2/docs/api/java/util/Vector.html
Data structures for using in multi thread.

I’d like to remind everybody that this is a wiki page.

Can someone please explain the differenct between a Vector and a ArrayList in java? I’ve never used a Vector.

Vector is synchronized
they work slower then ArrayList, but you can use them in 2 and more Thread at once.
(you can’t use ArrayList more then one Thread in one time, that’s call errors)

Simple example

ArrayList X
X have 5 elements
Thread 1 – remove last element
Thread 2 – add element to end
Can be situation when you receive:
Element 5 = null (because Thread 1 remove it ^^)
Before (1,2,3,4,5)
After (1,2,3,4,null,6)
or (1,2,3,4,null)

P.s Sorry don’t want modify first post , fear can write something not right on English :wink:

Well the difference is that Vector has some synchronization. To understand it correctly you have to understand the 5 level of synchronization for object and method

  1. Immutable : The object can’t be modified once created. This is the most safe level. No matter how many thread access this object you won’t run into any problem
  2. Thread-safe : The object contain enough internal synchronization (synchronized method) to be used without worry by multiple threads.
  3. Conditionnaly thread-safe : Same as thread-safe except that under some circonstances, you will need to provide external synchronization (outside of that object)
  4. Thread-Compatible : Can be use in multi-threaded environment but it is up to the programmer to do the synchronization
  5. Thread-hostile : Can’t be use in multi-threaded envrionment (Ex.: Thread.stop() - That method was deprecated because it releases the lock when it is called. Hence it could leave an object into an invalid state)

Vector are Conditionnally thread-safe. That means that most of the time you don’t need to provide external synchronization but in some case you might. One of that example is when iterating over the Vector and modifying it.
Collection.getSynchronizedCollection() - (or something like that) are also conditionnally thread-safe : meaning that you have to provide external synchronization for some operation.
ArrayList is thread compatible : meaning that if you want to use it in a multi-threaded environment you have to provide all the synchronization

There are no magic solution to synchronization, except for the human brain :slight_smile:

Collections.synchronizedList(new ArrayList())

Some people really don’t understand the concept of a wiki… :cranky:

lol :slight_smile:

Please consider moving content into the wiki article.

The created concurrency page should not indicate that synchronization is required for thread-safety…that’s so 80s.

It’s a wiki, correct it when it is added.

Don’t be afraid to edit. We’ll try not to slaughter anyone :slight_smile:

I disagree with the “General Advice”, always use the most specific type that you can so you can have access to all possible methods. If you are planning to switch out types later, you are doing something wrong. :slight_smile:

I can’t believe how full of nonsense that is. I can’t even begin to respond to it.