1

I have a List for Windows Performance Counters, which is static and cannot be changed at run-time. However, over the time this list has grown so large that it is extremely tedious to detect duplicates manually. For this I have written a tool which can run for checking the duplicates but still it is possible that people may forget to run that tool or are not aware of it.

I was to figure out if there is a way to detect the duplicates at compile time itself. The code looks something like this:

public enum SampleEnum
{
    [Description("Sample")]
    Sample,
}

And another class to define the Performance Counter:

public class PerfCounter
{
    public int CounterType { get; set; }
    public string CounterName { get; set; }
}

These two classes are used as follows:

public static class PerfCounterManager
{
    public static List<PerfCounter> GetCounters() 
    {
        return new List<PerfCounter> 
        {
            new PerfCounter
            {
                CounterTypeId = (int) SampleEnum.Sample1,
                CounterName = GetEnumDescription(CounterType.Sample1)
            },
            new PerfCounter
            {
                CounterTypeId = (int) SampleEnum.Sample2,
                CounterName = GetEnumDescription(CounterType.Sample2)
            },
        }
    }
}

The function GetCounters() may be called many times, but will not be modified except during compilation.

The error can get thrown not only because CounterTypeId can be duplicates, but also because CounterName which is the description of the enum can be duplicate. And because the list is very large, it is not possible to detect this error while someone is adding elements to the list. It will be very useful if this can be detected at compile time itself.

Vinay Pandey
  • 1,129
  • 3
  • 16
  • 33

2 Answers2

0

There is not much can be done at compile time short of some convention. It looks like you already have enum for values - not using something like Sample44 = 12 would prevent duplicate enum values. Some reasonable naming scheme for description could help with description duplicates.

Safe solution would be to add unit test that simply checks that condition - everyone runs unit tests and immediately will see the problem. (If you don't have unit tests - it is good excuse to start using them).

Alexei Levenkov
  • 98,904
  • 14
  • 127
  • 179
  • As I said, I already have a tool to check whether the Windows Performance Counters have been created successfully, but people (including myself) forget to run that tool many times - that's why it will be very helpful to detect duplicates at compile time and generate compiler warnings. – Vinay Pandey Feb 05 '14 at 02:35
  • @babbupandey, Why not to simply run "tool" as part of the build if you don't have/don't want unit tests? – Alexei Levenkov Feb 05 '14 at 02:38
0

Use a HashSet<T> or SortedSet<T> as the backing store for your List<T>. Something like the following, though you'll probably need a suitable IEqualityComparer to properly define your notion of uniqueness. This won't enforce uniqueness by throwing a compile-time error, but it will guarantee uniqueness. Might be a useful extension to modify things to do this and log a message regarding any lack of uniqueness, for diagnostic purposes...and so you can track down the guilty party and thrash them soundly :^)

public static class PerfCounterManager
{
  public static List<PerfCounter> GetCounters() 
  {
    return new List<PerfCounter> 
    {
      new SortedSet<PerfCounter>
      {
        new PerfCounter
        {
          CounterTypeId = (int) SampleEnum.Sample1,
          CounterName = GetEnumDescription(CounterType.Sample1)
        },
        new PerfCounter
        {
          CounterTypeId = (int) SampleEnum.Sample2,
          CounterName = GetEnumDescription(CounterType.Sample2)
        },
      }
    }
  }
}

[and by the way, while I love my iPad, for writing code, it's about the sickest thing I've ever used.]

Nicholas Carey
  • 71,308
  • 16
  • 93
  • 135