The tools that are part of the .NET Framework are located in the root directory for the version of the framework you are using. See the tool's documentation in the .NET Framework SDK for the abbreviated form of each switch.
1-1. Create a Console Application from the Command Line
Problem
Solution
How It Works
Declare a constructor for your form class that instantiates each of the form's controls and configures their initial state (size, color, position, content, and so on). Application entry point, creates an instance of the form and // starts a standard message loop on the current thread.
1-3. Create and Use a Code Module
To compile a source file named ConsoleUtils.cs (see recipe 1-1 for the contents) into a module, use the command csc /target:module ConsoleUtils.cs. The command csc /target:module ConsoleUtils.cs WindowsUtils.cs compiles two source files named ConsoleUtils.cs and WindowsUtils.cs to create the module named ConsoleUtils.netmodule.
1-4. Create and Use a Code Library from the Command Line
You must access the arguments specified on the command line when your application was executed. Alternatively, access the command line arguments from anywhere in your code using the static members of the System.Environmentclass.
1-6. Include Code Selectively at Build Time
If you use the ConditionalAttribute on a method, the compiler will ignore all calls to the method if the symbol specified by the ConditionalAttribute is not defined at the point of call. Additionally, the ConditionalAttribute specifies that calls to the DumpState method should be included in the assembly only if the DEBUG symbol is defined at compile time.
Notes
The methods in the Debug class are conditional on the definition of the symbol DEBUG, and the methods in the Traceclass are conditional on the definition of the symbol TRACE.
1-7. Access a Program Element That Has the Same Name As a Keyword
When you strongly name your assembly (discussed in Recipes 1-9), the compiler uses your private key to generate a digital signature (encrypted hash code) of the assembly manifest. To delete strong name keys from the StrongNameKeys container (as well as delete the container), use the sn -d StrongNameKeys command.
1-9. Give an Assembly a Strong Name
When building your assembly with the C# command line compiler, use the /keyfileor /keycontainer compiler switches to specify the location of your strong name key pair. The compiler switches to determine the location where the compiler can obtain your strongname key pair:.
1-11. Delay Sign an Assembly
Because there is no digital signature, you must configure the runtime on the local machine to stop verifying the strong assembly name using the sn -Vr Recipe01-11.exe command. After development is complete, you must re-sign the assembly to complete the strong name of the assembly.
1-12. Sign an Assembly with an Authenticode Digital Signature
Click Next on the introductory screen and you will see a file selection screen where you must enter the assembly name in the Authenticode character (see Figure 1-2). If you are signing an assembly with multiple files, specify the name of the file that contains the assembly manifest.
1-13. Create and Trust a Test Software Publisher Certificate
The certificate creation tool supports many arguments, and Table 1-2 lists some of the more useful ones. You should consult the .NET Framework SDK documentation for full coverage of the certificate creation tool.
1-14. Manage the Global Assembly Cache
When you are done using your test SPC, remove the trust from the root test CA using the setreg 1 false command. You can now Authenticode sign assemblies with your test SPC using the process described in recipes 1-12.
1-15. Prevent People from Decompiling Your Code
The best you can do is to use obfuscation and components compiled to native code to make your assemblies harder to decompile. Use an obfuscator to make your code hard to understand once it's decompiled.
1-16. Manipulate the Appearance of the Console
BackgroundColor Gets and sets the background color of the console using one of the values from System.ConsoleColorenumeration. ForegroundColor Gets and sets the console text color using one of the values from System.ConsoleColorenumeration.
2-1. Manipulate the Contents of a String Efficiently
If you set Length to a value less than the length of the current content, the content is truncated. If you set Length to a value greater than the length of the current content, the buffer is padded with spaces up to the specified length.
2-2. Encode a String Using Alternate Character Encoding
You obtain instances of specific encoding classes using the staticfactory Encoding.GetEncoding method, which accepts either the name or the code page number of the requested encoding scheme. Once you have an encoding object of the appropriate type, you convert a UTF-16 encoded Unicode string to a byte array of encoded characters using the GetBytesmethod.
2-3. Convert Basic Value Types to Byte Arrays
Calling ToString and passing an array of bytes as an argument will return a String object containing the hexadecimal value of each byte in the array separated by a dash, for example "34-A7-2C". Unfortunately, there is no standard method to reverse this process to get an array of bytes from a string with this format.
2-4. Base64 Encode Binary Data
Note If you base64 encode binary data to include as MIME data in an email message, note that the maximum line length allowed in MIME for Base64 encoded data is 76 characters.
2-5. Validate Input Using Regular Expressions
Specifies one or zero instances of the previous character or subexpression; For example, A?B matches B and AB, but not AAB. Specifies one or more instances of the previous character or subexpression; For example, A+B matches AB, AAB, AAAB, and so on, but not B.
2-6. Use Compiled Regular Expressions
Pattern, a string value that specifies the pattern that the regular expression matches (see recipe 2-5 for more details). This process creates an assembly that contains one class declaration for each compiled regular expression - each class is derived from Regex.
2-7. Create Dates and Times from Strings
The following example demonstrates the flexibility of the Parse method and the use of the ParseExact method. The simplest overload of the sort method sorts the objects contained in an array or ArrayList structure as long as the objects implement the System.IComparable interface and are of the same type.
2-10. Copy a Collection to an Array
Create a string array and use the ICollection.CopyTo // method to copy the contents of the ArrayList. Use ArrayList.ToArray to create a strongly typed string // array from the contents of the collection.
2-11. Use a Strongly Typed Collection
2-12. Create a Generic Type
When you implement the type, you replace the generic type names in the code instead of using specific type names. A generic type must be the same as another generic type (eg T1 must be the same as T3).
2-13. Store a Serializable Object to a File
The ArrayList object is then deserialized from the files and the content displayed on the console. Rebuild the lists of people from the binary and SOAP // serialization and display them to the console.
2-14. Read User Input from the Console
NET Framework 2.0 adds a ReadKeymethod method to the Consoleclass that allows input to be read from the console without waiting for the user to press Enter. By passing true as an argument to the ReadKeymethod overload, you can also prevent the key pressed by the user from responding on the console.
3-1. Create an Application Domain
Remember to store a reference to the new AppDomain since // this cannot be obtained any other way. Note You must keep a reference to the AppDomainobject when you create it because there is no mechanism to enumerate existing application domains from within managed code.
3-2. Create Types That Can Be Passed Across Application Domain Boundaries
The code creates a new application domain and instantiates the two remote objects in it (discussed in more detail in Recipes 3-7). Display the name of the application domain in which // each of the objects resides.
3-3. Avoid Loading Unnecessary Assemblies into Application Domains
Note Recipe 13-1 provides more details on creating serializable types, and Recipe 10-16 describes how to create removable types.
3-4. Create a Type That Cannot Cross Application Domain Boundaries
To ensure that a type is not serializable, ensure that it does not have the System.SerializableAttribute applied to the type declaration. Commonly used base classes that derive from MarshalByRefObject include System.ComponentModel.Component, System.IO.Stream, System.IO.TextReader, System.IO.TextWriter, System.NET.WebRequest, and System.Net.WebResponse.
3-5. Load an Assembly into the Current Application Domain
If the assembly does not have a strong name or is not found in the GAC, the runtime looks for applicable
3-6. Execute an Assembly in a Different Application Domain
The CLR does not start execution of the assembly in a new thread, so control will not return from the ExecuteAssembly method until the newly executed assembly completes. Display the command line arguments on the front screen with // the friendly name of AppDomain.
3-7. Instantiate a Type in a Different Application Domain
You create an application domain and then create your controller class in the application domain using CreateInstance. Create a PluginManager in the new application domain and // specify the default list of plugins to create.
3-8. Pass Data Between Application Domains
However, at times it is useful to transfer data between application domains in such a way that the data is easily accessible by all code within the application domain. After transferring a list of pets to another application domain for modification, the application displays both the original and modified lists.
3-9. Unload Assemblies and Application Domains
You remove an application domain using the AppDomain.Unload static method and pass it an AppDomain reference to the application domain you want to remove. While an application domain is unloading, the CLR calls the rounding method of all objects in the application domain.
3-10. Retrieve Type Information
A more flexible (but slower) alternative is to use the Type.GetType method to return a type reference for a named type. Test whether someObject is a TextReader or derived from // the Type.GetType and Type.IsSubclassOf methods.
3-12. Instantiate an Object Using Reflection
Once you have a Type instance, call its GetConstructor method to get a ConstructorInfo representation of one of the type's constructors. To get a ConstructorInfo representation of a parameterless (default) constructor, pass an empty Typearray (use the static field Type.EmptyTypeor new Type[0]);.
3-13. Create a Custom Attribute
The following example shows a custom attribute called AuthorAttribute, which you can use to identify the name and company of the person who created an assembly or class. The company property is public, making it an optional named parameter, but the name property is read-only - no setaccessor is declared - meaning it is not exposed as a named parameter.
3-14. Inspect the Attributes of a Program Element Using Reflection
The runtime host, the managed code that loads and executes the Common Language Runtime (CLR), determines the relationship between managed and unmanaged threads. This is a compiler extension only: the intermediate language (IL) generated is as if the correct delegate had been instantiated.
4-1. Execute a Method Using the Thread Pool
A private class used to pass data to the DisplayMessage method when it is // executed using the thread pool. The thread pool handles each work item in the order you add it to the work queue.
4-2. Execute a Method Asynchronously
A System.AsyncCallbackdelegate instance that references a method that the runtime will call when the asynchronous method completes. The referenced CallbackHandler // method is automatically called when the asynchronous method // completes, leaving that method free to continue processing.
4-3. Execute a Method Periodically
Once you have created aTimerobject, you can modify the intervals used by the timer using the change method, but you cannot change the method that is called. The example allows you to enter a new millisecond interval on the keyboard, which is applied using the Timer.Changemethod.
4-4. Execute a Method at a Specific Time
RegisterWaitForSingleObjectmethod, register the method to be executed and the WaitHandle object that triggers execution when signaled. You can configure the thread pool to execute the method only once or to automatically re-register the method for execution each time the WaitHandleis signals.
4-6. Execute a Method Using a New Thread
A utility method for displaying useful trace information to the // console along with details of the current thread. The // method displays a message to the console a specified number of // times, sleeping between each message for a specified duration.
4-7. Synchronize the Execution of Multiple Threads Using a Monitor
The thread that currently owns the lock can call Monitor.Wait, which will release the lock and place the calling thread on the lock queue. When the user presses Enter the first two times, the work items (strings in the case) are added to the work queue and Monitor.Pulse is called to release one waiting thread for each work item.
4-8. Synchronize the Execution of Multiple Threads Using an Event
WaitAny A static method that causes the calling thread to enter aWaitSleepJoinstate and wait for any one of the objects in aWaitHandlearray to be signaled. Terminate the DisplayMessage thread and wait until it // completes before disposing of the EventWaitHandle.
4-9. Synchronize the Execution of Multiple Threads Using a Mutex
In a loop, the method waits to acquire a Mutex before displaying a // message to the console and then waits one second before releasing the // Mutex. Terminate the DisplayMessage threads and wait until they // complete before disposing of the Mutex.
4-10. Synchronize the Execution of Multiple Threads Using a Semaphore
In a loop, the method waits to receive a Semaphore before displaying a // message to the console, and then waits one second before releasing // the Semaphore. Terminate the DisplayMessage threads and wait for them // to complete before disposing of the Semaphore.
4-11. Synchronize Access to a Shared Data Value
Add Adds two to long values and sets the value of the first argument to the sum of the two values. The example does not demonstrate Interlocked in the context of a multithreaded program and is provided only to clarify the syntax and effect of the various methods.
4-12. Know When a Thread Finishes
The easiest way to test if a thread has finished executing is to test the Thread.IsAliveproperty. If you specify a timeout value, Join returns true if the thread terminates, and returns false if Join timed out.
4-13. Terminate the Execution of a Thread
Use lock statements in your code to synchronize thread access to the collection or to access the collection through a thread-safe wrapper. The collection classes such as HybridDictionary, ListDictionary, and StringCollection from System.Collections.Specializednamespace do not implement aSynchronizedmethod.
4-15. Start a New Process
Run notepad.exe and pass the name of the file to open as the // command line argument. Run notepad.exe and pass the name of the file to open as the // command line argument.
4-16. Terminate a Process
CloseMainWindow returns true if the close message was sent successfully, but it does not guarantee that the process is actually terminated. The following example starts a new instance of Notepad, waits 5 seconds, and then terminates the Notepad process.
4-17. Ensure That Only One Instance of an Application Can Execute Concurrently
Provide the path of the resource to the constructor, and then you will be able to retrieve information through the properties of the class. Note Instead of using the instance methods of the FileInfo and DirectoryInfoclasses, you can use the static File and Directory classes (note that a class corresponding to the DriveInfo class does not exist).
5-2. Set File and Directory Attributes
For example, if you bitwise AND a value of 00100001 (representing an individual file's archive and read-only attributes) with the enumerated value 00000001 (representing the read-only flag), the resulting value will be 00000001—that will have a1 only where it matches in both values. The following example takes a read-only test file and checks for the read-only attribute.
5-4. Calculate the Size of a Directory
5-5. Retrieve Version Information for a File
You can use an enclosure (such as an asterisk or an empty TreeNode) in any directory branches that are not filled. This allows you to fill in parts of the directory tree as they are displayed.
5-7. Read and Write a Text File
When using ASCII encoding in .NET, the bits will be padded and the resulting byte array will have 1 byte for each character. The resulting byte array will have 1 byte for each character (provided there are no extended characters).
5-8. Read and Write a Binary File
5-9. Read a File Asynchronously
The following is an example of the output you see when you run this test.
5-10. Find Files That Match a Wildcard Expression
5-11. Test Two Files for Equality
5-12. Manipulate Strings Representing Filenames
The advantage of this approach is that a backslash (\) is automatically added to the path name if necessary. You can use the Path.GetInvalidPathChars method to get an array of characters that are illegal in path names.
5-13. Determine If a Path Is a Directory or a File
5-14. Work with Relative Paths
The relative path 'file.txt' will automatically become 'c:\temp\file.txt'. Change current directory to c:\.
5-15. Create a Temporary File
5-16. Get the Total Free Space on a Drive
The following console application shows the free space available using the DriveInfoclass for the given drive or for all logical drives if the application is not passed any arguments.
5-17. Show the Common File Dialog Boxes
FolderBrowserDialog, which allows the user to select (and optionally make) a folder, as shown in Figure 5-3. When using OpenFileDialog or SaveFileDialog, you must set the filter string that specifies the allowed file extensions.
5-18. Use an Isolated Store
When you create isolated storage files, the data is automatically serialized to a unique location in the user profile path (typically a path like C:\Documents and Settings\[username]\Local Settings\Application Data\isolated storage\[guid_identifier]) . Access isolated memory for the current user and compose // (which is equivalent to the first example).
5-19. Monitor the File System for Changes