March 2008 Blog Posts
My previous post discussed the general reasons for branching and illustrated structures that support it. In this post I plan to expand on the reasons to use for branching and strategies teams may adopt to make effective use of branching throughout the development lifecycle.There are a number of reasons why you may wish to use branching in your system. Some of the major ones are:To allow the development team to be more effectively utilised. You will not necessarily want or need the entire team to be working on stabilising a version rather than working on new features. Additionally where breaking...
Consider a simple solution structure in source control such as that shown below. It is based at the root of the source control structure, and the projects of the solution are at the first level of the source control structure.This is a typical naive usage of source control. It works in that it allows developers to share their changes and provides history for all changes over time. Unfortunately, this structure is not without drawbacks. I'll start with some of the issues with the structure of the project itself and work up to larger issues with the overall organisation.One of the...
The structure contained within a source control repository looks very much like a file system. It contains what is (at least conceptually) a structure of directories and files. Where the repository extends this view is in its inclusion of history information. Items in the repository are given a version number on creation. On every modification a new version of the item is recorded. This is done in an additive fashion such that existing versions are immutable (barring special purpose administrative tools). In addition to the item itself a version will contain metadata such as a timestamp and the user who...
It's previously been established that I have a deep and abiding distaste for switch statements. This post will discuss alternate mechanisms that display superior maintainability and flexibility.Let's take a trivial example switch statement:var action = Console.ReadLine();
switch (action)
{
case "blah":
Console.WriteLine("All a bit blah.");
break;
case "stuff":
Console.WriteLine("Stuff happened.");
break;
case "other stuff":
Console.WriteLine("Other stuff happened.");
...
Although source control systems can detect and assist in the resolution of conflicting edits this is not sufficient to prevent developers from checking in incompatible changes. If the behaviour or interface of a type or collection of types is modified by a developer it is reasonable to assume that they will make appropriate modifications elsewhere in the system to account for these changes. However other developers working concurrently will not have these changes and will produce code that uses the old behaviour.As an example, take the TestItem class from my previous post. Developer A modifies the signature of the CalculateResult...
My previous post discussed the basic get and checkin operations that are key to the operation of source control. It also indicated that these operations are not in practice sufficient to build a usable change control system. This post will discuss why and go through the mechanisms source control systems use to address these problems.Take an example system which contains the class TestItem.cs, defined as:public class TestItem{ public int FirstValue { get; set; } public int SecondValue { get; set; } public int CalculateResult() ...
The fundamentals of source control essentially boil down to two elements: Repositories and Working Copies. All activities perfomed using source control involve interaction with one or both of these elements.The repository is the ultimate source of truth in the system. It contains the latest version of every item under source control. Additionally it contains a history of all the revisions of each item. This allows the state of the repository at any point in time to be recreated. By querying the repository you can determine such things as what changes were made in particular time periods, what changes a specific...
Roland Weigelt's GhostDoc is a Visual Studio add-in that automatically generates C# XML comments. By examining property, method and parameter names it generates a comment block that contains the core comment elements. I find it particularly useful in correcting comment blocks when the parameter list of a method changes.Because it generates the comment from an examination of the code it doesn't add information that cannot be inferred from the code. Therefore in almost all cases the comment block still needs to be edited to include more descriptive information. The advantage of using GhostDoc is that it does the obvious, tedious...
Yesterday's example showed how to use anonymous methods to apply logic to disparate items. This example was written in C# 2.0. Today I'll demonstrate how to convert this to C# 3.0 and use lambda expressions instead of anonymous methods.I'll start with the TestItem class, which can be significantly simplified. The new class is:public class TestItem
{
public int FirstValue
{ get; set; }
public int SecondValue
{ get; set; }
}
This converts the properties to automatic properties and loses the constructors as I'll be using the new object initialisers functionality...
My previous post suggested that it is possible to apply the same logic to elements that are disparate, that is do not have a common base class or interface that is relevant to the operation. This post describes a method of doing this using anonymous methods. I will use a simple example of summing values, but the principal is applicable generally, and is not specific to looping.Take for instance the following code:List<int> integerList = new List<int>();for (int initialValue = 1; initialValue <= 5; initialValue++){ integerList.Add(initialValue);}int sum = 0;foreach (int value in integerList){ sum...
Some applications appear to have trouble accepting the inevitable. They will do almost anything to avoid crashing, including any and all errors that attempt to tell them that maybe it's time to let go. This seems to come from a developer mentality that assumes that the end user is willing to put up with your application being wrong, consuming excessive system resources or breaking the system on which it runs rather than risk being separated from it. These developers really need to get over themselves, their application really isn't that important.Sometimes when you're caught up in the minutia of developing...
Unless checked the length of methods tends to grow without bound. Changes to functionality result in a developer adding additional functionality to an existing method to acheive their current requirement. The method gets longer and more complex, and this has a number of negative consequences.Beyond a point the human mind simply can't deal with complexity efficiently. This leads to fragile, buggy code that can't be altered because the side effects cannot be adequately predicted.As logic is encapsulated in large blocks it becomes more difficult to reuse the existing code. This leads duplicate logic tends to proliferate in the codebase. Duplicate
logic...
Lutz Roeder .NET Reflector is a tool that should be in the toolkit of every .NET developer. It is, as its website described it, a "class browser, explorer, analyzer and documentation viewer for .NET". It allows you to crack open any (non-obfusicated) .NET assembly to see the types inside. It can also analyse the type hierarchy and the use of types by other types both in the same assembly and in other assemblies. The decompiler can decompile types into a variety of languages, including IL, C#, VB.NET and Delphi.There are two primary questions I've received when telling people about .NET...
One of the defining moments in my career as a software developer came before I was getting paid to cut code. One of my uni courses required the development of a program to do read a bunch of numbers from a file then add them and display the result. I decided to do this using 80x86 assembler, which we were learning in this unit. I thus spent a weekend writing an assembler program than used DOS interrupts to do this. It had to do things like manage it's own buffer, moving partial data to the start of the buffer then...
One of the features that separates earlier systems I've designed from more recent practice is the use of prefixes in database item names. Early on I developed a pattern of giving tables a two character prefix that grouped them, and columns a four character prefix that identified the group and specific table. This was primarily relevant for foreign key columns to identify where the table they were referring to.This is not a practice I use or recommend today. There are a number of reasons for this:The additional information was rarely helpful. If the names of your tables are sufficiently close...
Google alleges that no one has every used it before. Except in the Visual SourceSafe specification documents I suspect...
This is the first in what may (or may not) be a series of posts on source control written to prepare for a presentation I'm doing on this topic.Source control is one of the fundamental elements of any professional software development effort. Desirable in single person development, it is mandatory in a team environment.The naive view of source control is that it is a backup mechanism to guard against the loss of work due to factors such as failure of a development system. This is an important function but represents only a small fraction of the worth of a source...
Which means it's still missing features and quite buggy. But my pain level in editing C# 3.0 has subsised somewhat (unless LINQ is involved). I know a lot of people who develop without Resharper. I don't know how they manage. Even on large solutions with noticable slowdowns I find the pain of its abscence to be too great.
I've wrriten a whole lot of framework code. I've written a variety of factory objects, component base classes and even an Object Relational Mapper. And if I was doing it all again, I wouldn't write any of them.My use of factory objects has dropped precipitously now that I'm using dependency injection (I tend to prefer Spring.NET, I know Castle partisans and I keep meaning to have a look at StructureMap). These existing DI frameworks provide a large amount of functionality and I didn't have to write it.I few years back I wrote my own system for doing ORM. It tracked...
I've decided to move my blog over to DasBlog. Adding features to my own system was taking time away from other projects I wanted to work on. This will result in all new URLs and a period of DNS uncertainty as I move over to my new hosting provider.