Why is DataTable faster than DataReader

I see three issues:

  1. the way you use a DataReader negates it’s big single-item-in-memory advantage by converting it to list,
  2. you’re running the benchmark in an environment that differs significantly from production in a way that favors the DataTable, and
  3. you’re spending time converting DataReader record to Artifact objects that is not duplicated in the DataTable code.

The main advantage of a DataReader is that you don’t have to load everything into memory at once. This should be a huge advantage for DataReader in web apps, where memory, rather than cpu, is often the bottleneck, but by adding each row to a generic list you’ve negated this. That also means that even after you change your code to only use one record at a time, the difference might not show up on your benchmarks because you’re running them on a system with lot of free memory, which will favor the DataTable. Also, the DataReader version is spending time parsing the results into Artifact objects that the DataTable has not done yet.

To fix the DataReader usage issue, change List<ArtifactString> to IEnumerable<ArtifactString> everywhere, and in your DataReader DAL change this line:

artifactList.Add(artifact);

to this:

yield return artifact;

This means you also need to add code that iterates over the results to your DataReader test harness to keep things fair.

I’m not sure how to adjust the benchmark to create a more typical scenario that is fair to both DataTable and DataReader, except to build two versions of your page, and serve up each version for an hour under a similar production-level load so that we have real memory pressure… do some real A/B testing. Also, make sure you cover converting the DataTable rows to Artifacts… and if the argument is that you need to do this for a DataReader, but not for a DataTable, that is just plain wrong.

Leave a Comment