4

I recently got access to a very old C# code base (very old meaning .NET 1.1 and C# 1.2) in order to find places that could be improved. It is like a window to the past when a bow was the most powerfull weapon. I have never had the opportunity to willingly code in C# version lesser than C# 2 before.

Basically, what I have found is that there is a whole bunch of large ArrayLists for storing numbers and structs. By large I mean tens or hundreds of thousand of values. Something like

ArrayList numbers = new ArrayList();
for(int i = 0; i < BIG_CONSTANT; i++)
    numbers.Add(someNumberReturnedFromMethod);

These lists are sorted on some place then again sorted by a different standard on another place, or there are searches performed on them.

Knowing that ArrayList works with objects results in two problems I came up with

  • no type-safety
  • boxing and unboxing everywhere

So the question is, how to solve this without the aid of generics? I definitely will not make classes from these structs in order to remove un/boxing, because with so many data, this really makes difference (tested).

I thought about creating custom array lists that would work with my structs instead. Do I have to create a custom array list implementation for every struct there is? Thinging about it, it would mean to define my own IEnumerable, ICollection and IList for each of these structs, right?

I think that it could be a good cost to pay in order to get more performing and type-safe system, but before trying it out I would like to know your opinion.

Ondrej Janacek
  • 12,486
  • 14
  • 59
  • 93
  • 1
    You're struck with .net 1.1? When you plan to improve the project why not use atleaset .net2.0? – Sriram Sakthivel Nov 28 '13 at 14:00
  • 1
    If your actual question is _"What can I replace my `ArrayList`s with in order to improve performance"_, I'm afraid the answer is _"Benchmark it"_. You obviously know about the alternatives, but whether any of them make any sense probably entirely depends on how they are being used in that project. – CodeCaster Nov 28 '13 at 14:04
  • @SriramSakthivel I wish it was that easy. It is not like I'm going to say to a customer - "Hey, I will install .NET 2.0 on your server to see if it works better and if not ...". They don't want to here that. – Ondrej Janacek Nov 28 '13 at 14:22
  • @CodeCaster I have an alternative, yes, but I would like to consult it here, first. Benchmarking is sure thing. I also thought that this could be an interesting question for SO folk. – Ondrej Janacek Nov 28 '13 at 14:24
  • Arrays don't lead to boxing, and they can be sorted. So your example could read: `NumberStruct[] numbers = new NumberStruct[BIG_CONSTANT]; for(int i = 0; i < BIG_CONSTANT; i++) numbers[i] = someNumberReturnedFromMethod;`. Clearly the problem is that arrays are fixed-sized, but I think you would use arrays a lot more if you didn't have access to (truly) generic types, such as `List<>`. – Jeppe Stig Nielsen Nov 28 '13 at 14:31

1 Answers1

3

Without generics you cannot create a collection that avoids boxing with value types. But you can create specialized collections for concrete value types.

Here's an idea: Create your own version of ArrayList but use T4 templates to generate specialized versions for every concrete type you care about. That gives you, without code duplication, an ArrayListInt32, an ArrayListSingle and so on.

This removes any performance penalty from the boxing and restores type safety.

Actually, Java has a similar problem because due to type erasure they cannot use generics to avoid boxing. They do have some specialized array list classes in newer versions. Thank god C# does implement true generics in recent versions.

usr
  • 168,620
  • 35
  • 240
  • 369
  • 1
    I used T4 templates for structuring an email body, but I would have never thought about using it for this. Nice point indeed! – Ondrej Janacek Nov 28 '13 at 14:19