1. Program to Interfaces Whenever Possible
The .NET Framework contains both classes and interfaces. When you write routines, you will find that you probably know which .NET class you're using. However, your code will be more robust and more reusable if you program using any supported interfaces instead of the class you happen to be working with at the time
2. Use Properties Instead of Raw Data
With the addition of properties as language elements, there is absolutely no reason to declare data elements with any access level greater than private. Because client code will view properties as data elements, you don't even lose the convenience of working with simple data elements in classes. In addition, using properties gives you more flexibility and more capabilities. Properties provide better encapsulation of your data elements. Properties let you make use of lazy evaluation to return data. Finally, properties can be virtual. They can even be abstract. You can also declare properties in interfaces.
3. Use Delegates for Producer/Consumer Idiom
When you create a class that implements the producer idiom, use a delegate to notify consumers. This will be a more flexible way to implement this idiom than interfaces. Delegates are multicast, so you can support multiple consumers without creating extra code. Also, you lower the coupling between classes by using the delegate model rather than a full interface model
4. Pay Attention to Initialization Order
The C# language adds the concept of initializers on member variable declarations. These initializers get executed before the body of the constructor gets executed. In fact, variable initializers get executed before the base class's constructor gets executed
Read the complete article here...