14.2. The System.Collections Classes

Table 14.2 lists the classes of the System.Collections namespace along with their Java equivalents. Some of the classes in Table 14.2 share a common set of behavior rules, discussed next.

14.2.1. Thread Safety

By default, the C# collection classes are not thread-safe and therefore are similar to the Java 2 collections. Therefore, the C# Hashtable (Table 14.2) is equivalent to Java's non-thread-safe java.util.HashMap and not to the thread-safe java.util.Hashtable. Most of the C# collection classes have a Synchronized method that provides a thread-safe wrapper of the class. Java instead provides a method called Collections.synchronized Collection() on the java.util.Collections object, and you use this method to get a thread-safe wrapper for the collection classes.

For example, to get a thread-safe ArrayList in C# you write the following:

ArrayList states = ArrayList.Synchronized (new ArrayList());

14.2.2. Type Safety

Java collections do not enforce type safety, and therefore objects obtained from the collection must be cast to the specific type. Nor does Java provide any infrastructure for writing type-safe collections.

C#, on the other hand, provides the classes CollectionBase and DictionaryBase, which are abstract implementations of type-safe collections. These classes have the requisite hooks that subclasses can implement to enforce type safety. You will see an example of this later in the chapter.

Table 14.2. Classes of the System.Collections Namespace
C# ClassJava ClassC# Description
ArrayListArrayListA list-based data structure whose size is dynamically increased. Allows array-like indexed access.
BitArrayBitSetAn array of bit values that can be either 1 (true) or 0 (false).
CaseInsensitiveComparerN/ACompares two objects, ignoring case sensitivity of strings.
CaseInsensitiveHashCodeProviderN/AProvides a hash code for an object, ignoring the case of the strings.
CollectionBaseN/AAn abstract base class for storing strongly typed objects.
ComparerN/AProvides case-sensitive comparison of objects.
DictionaryBaseN/AAn abstract base class for storing strongly typed key-value pairs.
HashtableHashMapRepresents a collection of key-value pairs.
QueueLinkedListImplements a first in first out (FIFO) collection.
ReadOnlyCollectionBaseN/AAn abstract class for storing strongly typed read-only values.
SortedListTreeMapA collection indexed by the key of a key-value pair and sorted by the key.
StackStackImplements a last in first out (LIFO) collection.

14.2.3. Immutability

Immutable collections are useful when you don't want the collection to be modified. In the following code snippet, a class creates an ArrayList, populates it with U.S. states, and returns this list. This list is mutable because the caller of the GetStates() method can add, delete, or modify the list.

public ArrayList GetStates() {
  ArrayList states = new ArrayList();
  //Populate states from database;
  return states;
}

To enforce immutability of the collections, you must make them read-only. In Java, you use the Collections.unmodifiableCollection method of the java.util.Collections class to make the collection unmodifiable (in other words, the structure of the collection cannot be modified).

C# provides two levels of immutability. Some of the C# collection classes (ArrayList, Hashtable) implement two public properties (IsFixedSize and IsReadOnly) along with the corresponding methods FixedSize and ReadOnly, which mark the collection as fixed-size and read-only, respectively. In a FixedSize collection you can modify the individual elements of a collection, but you cannot add or delete from the collection (change its size). In a ReadOnly collection you cannot add, delete, or modify the elements of the collection. To make the GetStates() method return an immutable list you would have to do the following:

public ArrayList GetStates() {
  ArrayList states = new ArrayList();
  //Populate states from database;
  return ArrayList.ReadOnly(states);
}

14.2.4. Accessibility

The collection classes ArrayList and Hashtable provide indexers. (Indexers are discussed in detail in Chapter 17.) Indexers allow these collections to be accessed like arrays. Instead of using the Java-like Get() and Set() methods, you should use the indexer notation to get and set elements of the collection. The following snippet prints the elements of the ArrayList using the array-like indexed notation. Even a Hashtable with string-based keys can be accessed this way.

ArrayList list = new ArrayList();
  for (int j = 0; j < list.Count; ++j) {
  Console.WriteLine(list[j]);
}

object value = new object();
Hashtable hash = new Hashtable();
hash["key"] = value;

You can use C# collections to store primitives directly without converting them into their object representations. Therefore, the following snippet is perfectly legal in C#:

ArrayList list = new ArrayList();
list.add(1);
list.add(2);
list.add(3);

This is because of the automatic boxing and unboxing of value types, as described in Chapter 7.

Now let's explore the classes shown in Table 14.2 and examine them through examples.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.149.26.246