7

I'm working on a webservice and I'm returning JSON. However, I'm returning a List<KeyValuePair<string, int>>, since that's all I'm really ever going to be dealing with (property => value)

Now sometimes I myself will be calling these functions to aggregate the results, so I end up with something like

List<KeyValuePair<string, int>> myList = resultList.where(o => o.Key =="StringKEY");

and sometimes

List<KeyValuePair<string, int>> myList = resultList.sum(o => o.Key =="StringKEY");

My question is, would it be more efficient to do the following (custom class vs dictionary):

List<MyObject> myObj = resultObjList.where(o => o.Property1 == "stringProperty")

and so on.

Is there any benefit to using custom objects? I will not ever need to be adding properties, and in this case I can say there will never be a need for additional properties.

1

3 Answers 3

7

You're asking what is the difference between a KeyValuePair and a two-property object? There is none, KeyValuePair is a two-property object. Actually, there might be a difference: KeyValuePair is a value type and your custom object will probably be a reference type. The difference between a reference type and value type can have an impact on the performance (especially in some specific environments, like XNA on XBox). But if this difference is important for you, you can always make your custom type into a value type.

So, my advice is to use KeyValuePair for things that actually are a key and a value. If the relation between the two values is different, you should create your custom type, for readability sake.

Another option in C# 7.0 and newer is to use tuples. They're value types, just like KeyValuePar, but using them does not imply you have a key and a value.

3
  • thanks for that answer.. since the application is for a webservice and response times are crucial to providing good service, i need the optimum solution, which you've provided.. thank you!
    – hanzolo
    Jan 24, 2012 at 21:12
  • 1
    @hanzolo, if response times are crucial, you should base your decisions on profiling your code, not something someone on the internet said.
    – svick
    Jan 24, 2012 at 21:15
  • but i snopes'd it! ;-)
    – hanzolo
    Jan 24, 2012 at 22:20
3

Profiling whenever in doubt is definitely a good way to go. Since I can't profile your code (nor would I probably want to), I'll share my two cents of theory:

Both two-property object and your KeyValuePair essentially store exactly the same data and in both instances you are storing your data in a List collection which means that in order to find individual entries, you have to perform a full collection scan, O(n) operation.

Theoretically, KeyValuePair<> might be tad faster (not sure if even profiler would notice it) because there's one less level of indirection that has to take place.

  • ListEntry(KeyValuePair) --> string; ListEntry(KeyValuePair)
  • ListEntry(obj ref) --> Object --> string; ListEntry(obj ref) --> Object(int)

However, one change that you could do to improve performance if your collection gets rather large, is use a different type instead of a List. With List you are stuck with linear searches and can't really get away from that (unless you'll spend extra effort manually sorting it, but why would you).

Since you have a notion that each object has a key, use Dictionary<> or SortedDictionary<> which would be keyed of your key.

In this case, just to give you a comparison, if your List has 1000 entries and you need to find one, worst case will require you to do 1000 compares. If you use a keyed collection, in worst case, you will only perform 10 compares. When performing a sum or looking for multiple items with same key, they will all be located together in the collection, so it also becomes much easier (computationally) to do that operation, rather than searching for them everywhere.

0

I think you'll be hard pressed to find any real-world performance difference given this is a web service -- the fastest HTTP request will still be orders of magnitude slower than any sort of micro-optimization you can get here.

Code-wise, unless I am actually dealing with an arbitrary list of keys, I'd run with a good old fashioned POCO. Intellisense and compile-type checking are cool.

1
  • 2
    in terms of HTTP request round-trip time, you are correct. timing difference by this optimization is negligible because of network overhead on top of it. But what about 5,000 requests hitting the webserver? If you reduce CPU requirements of your algorithms, you may not improve single-request response time, but you could increase rate of requests serviced. Then again, what's the realistic request rate for a typical web page.
    – DXM
    Jan 25, 2012 at 19:16

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.