Document directory
- Abstract: C # 3.0cookbook Chinese Version C # 3.0cookbook Chinese Version focuses on solving various problems encountered by C # programmers when developing applications, and organizes the contents of this book. These solutions are called secrets; each secret contains a question, his solution, and related information. This section describes how to replace hashtable with the corresponding generic type.
- Label: Generic C #3.0 0 cookbook C # 3.0cookbook Chinese Version
- Oracle helps you gain an accurate insight into each logistics Link
4.9 replace hashtable with the corresponding generic
Problem
You want to use its generic version to replace all hashtable objects to enhance application performance and make the code easier to process.
Solution
Use the type-safe generic class system. Collections. Generic. dictionary to replace all the system. Collections. hashtable classes that appear.
The following is a simple example of using the system. Collections. hashtable object:
public static void UseNonGenericHashtable() { Console.WriteLine("\r\nUseNonGenericHashtable"); // Create and populate a Hashtable Hashtable numbers = new Hashtable() { {1, "one"},"one"}, // Causes a boxing operation to occur for the key {2, "two"} }; // Causes a boxing operation to occur for the key // Display all key/value pairs in the Hashtable // Causes an unboxing operation to occur on each iteration for the key foreach (DictionaryEntry de in numbers) { Console.WriteLine("Key: " + de.Key + "\tValue: " + de.Value); } Console.WriteLine(numbers.IsReadOnly); Console.WriteLine(numbers.IsFixedSize); Console.WriteLine(numbers.IsSynchronized); Console.WriteLine(numbers.SyncRoot); numbers.Clear(); } |
The same Code for using the system. Collections. Generic. dictionary <t, u> object is given below:
public static void UseGenericDictionary() { Console.WriteLine("\r\nUseGenericDictionary"); // Create and populate a Dictionary Dictionary<int, string> numbers = new Dictionary<int, string>() { { 1, "one" }, { 2, "two" } }; // Display all key/value pairs in the Dictionary foreach (KeyValuePair<int, string> kvp in numbers) { Console.WriteLine("Key: " + kvp.Key + "\tValue: " + kvp.Value); } Console.WriteLine(((IDictionary)numbers).IsReadOnly); Console.WriteLine(((IDictionary)numbers).IsFixedSize); Console.WriteLine(((IDictionary)numbers).IsSynchronized); Console.WriteLine(((IDictionary)numbers).SyncRoot); numbers.Clear(); } |
Discussion
For the simple implementation of hashtable in the application, this replacement should be quite easy. However, there are some things to be aware. For example, the generic class dictionary does not implement the icloneable interface, while the hashtable class implements this interface.
Table 4-3 shows equivalent members simultaneously implemented in two classes.
Table 4-3: equivalent members in hashtable and generic class dictionary
| Members in the hashtable class |
Equivalent member in generic dictionary |
| None |
Comparer attributes |
| Count attribute |
Count attribute |
| Isfixedsize attribute |
(Idictionary) mydict). isfixedsize |
| Isreadonly attribute |
(Idictionary) mydict). isreadonly |
| Issynchronized attributes |
(Idictionary) mydict). issynchronized |
| Item attribute |
Item attribute |
| Keys attributes |
Keys attributes |
| Syncroot attributes |
(Idictionary) mydict). syncroot |
| Values attributes |
Values attributes |
| Add Method |
Add Method |
| Clear Method |
Clear Method |
| Clone Method |
Uses an overloaded constructor that accepts an idictionary <t, u> type. |
| Contains Method |
Containskey Method |
| Containskey Method |
Containskey Method |
| Containsvalue Method |
Containsvalue Method |
| Copyto Method |
(Icollection) mydict). copyto (ARR, 0) |
Table 4-3: equivalent members in hashtable and generic class Dictionary (continued)
| Members in the hashtable class |
Equivalent member in generic dictionary |
| Remove Method |
Remove Method |
| Synchronized static method |
Lock (mydictionary. syncroot ){...} |
| None |
Trygetvalue Method |
In table 4-3, in some cases, there is no one-to-one relationship between hashtable members and generic class dictionary members. Starting from the attribute, note that only the attributes count, keys, values, and item exist in both classes. To compensate for the missing attributes in the dictionary class, you can forcibly convert them to idictionary. The following code shows how to use these forced conversions to obtain missing attributes:
Dictionary<int, string> numbers = new Dictionary<int, string>(); Console.WriteLine(((IDictionary)numbers).IsReadOnly); Console.WriteLine(((IDictionary)numbers).IsFixedSize); Console.WriteLine(((IDictionary)numbers).IsSynchronized); Console.WriteLine(((IDictionary)numbers).SyncRoot); |
Note: because no code can return the synchronous version of the generic dictionary, the issynchronized attribute always returns false. The syncroot attribute always returns the same object that calls it. Essentially, this property returns the this pointer. Microsoft decided to cancel the ability to create a synchronous package from any generic collection class.
As an alternative, they recommend that you use the lock keyword to lock the entire set or another type of synchronization object that suits your needs.
Because the clone method is also missing in generic class Dictionary (this is because this class does not implement the icloneable Interface), you can replace it with an overloaded constructor, which accepts an idictionary <t, u> type:
// Create and populate a Dictionary Dictionary<int, string> numbers = new Dictionary<int, string>() { { 1, "one" }, { 2, "two" } }; // Display all key/value pairs in the original Dictionary. foreach (KeyValuePair<int, string> kvp in numbers) { Console.WriteLine("Original Key: " + kvp.Key + "\tValue: " + kvp.Value); } // Clone the Dictionary object. Dictionary<int, string> clonedNumbers = new Dictionary<int, string>(numbers); // Display all key/value pairs in the cloned Dictionary. foreach (KeyValuePair<int, string> kvp in numbers) { Console.WriteLine("Cloned Key: " + kvp.Key + "\tValue: " + kvp.Value); } |
The contains and copyto methods are missing in the dictionary class. You can easily copy the contains method in the dictionary class. In the hashtable class, both the contains method and the containskey method show the same behavior. Therefore, you can simply use the dicinskey method of the dictionary class to simulate the contains method of the hashtable class:
// Create and populate a Dictionary Dictionary<int, string> numbers = new Dictionary<int, string>() { { 1, "one" }, { 2, "two" } }; Console.WriteLine("numbers.ContainsKey(1) == " + numbers.ContainsKey(1)); Console.WriteLine("numbers.ContainsKey(3) == " + numbers.ContainsKey(3)); |
The copyto method can also be easily simulated in the dictionary class, but it requires more work:
// Create and populate a Dictionary Dictionary<int, string> numbers = new Dictionary<int, string>() { { 1, "one" }, { 2, "two" } }; // Display all key/value pairs in the Dictionary. foreach (KeyValuePair<int, string> kvp in numbers) { Console.WriteLine("Key: " + kvp.Key + "\tValue: " + kvp.Value); } // Create object array to hold copied information from Dictionary object. KeyValuePair<int, string>[] objs = new KeyValuePair<int, string>[numbers.Count]; // Calling CopyTo on a Dictionary // Copies all KeyValuePair objects in Dictionary object to objs[] ((IDictionary)numbers).CopyTo(objs, 0); // Display all key/value pairs in the objs[]. foreach (KeyValuePair<int, string> kvp in objs) { Console.WriteLine("Key: " + kvp.Key + "\tValue: " + kvp.Value); } |
Calling the copyto Method for a dictionary object involves creating an array of keyvaluepair <t, u> objects. After the copyto method is called, the array is used to save all keyvaluepair in the dictionary object <t, u> object. Next, the dictionary object numbers is forcibly converted to the idictionary type so that the copyto method can be called. Once the copyto method is called, The objs array contains copies of all keyvaluepair <t, u> objects in the original numbers object. Note: Use the foreach loop to iterate the objs array in the same way as the numbers object.
Reference
The "system. Collections. hashtable class" and "system. Collections. Generic. dictionary class" topics in the msdn document.