Back to Projects

Project case study

Data Structure Benchmark in C++

This project implements several data structures behind one set-like interface and compares their running time for insertion, removal, and search workloads.

Every structure implements DataStructure in data_structure.h:

virtual void insert(int value) = 0;
virtual void remove(int value) = 0;
virtual bool search(int value) const = 0;

The benchmark uses unique positive integers from 1 to N. It is intended as an educational comparison of these implementations, not as a replacement for production containers or a statistically rigorous benchmark suite.

Implemented data structures

Data structureHeaderExpected operation cost
Adelson-Velsky-Landis (AVL) treeadelson_velsky_landis_tree.hO(log N) insert, remove, and search
Binary heapbinary_heap.hO(N) for this interface because duplicate checks, arbitrary removal, and search scan the heap
Binary search treebinary_search_tree.hAverage O(log N), worst-case O(N)
Binary search triebinary_search_trie.hO(W), where W is the fixed integer bit width
Cuckoo hash tablecuckoo_hash_table.hAverage O(1); insertion may trigger a rebuild
Hash table with separate chaininghash_table.hAverage O(1), worst-case O(N)
Linked listlinked_list.hO(N) insert, remove, and search
Red-black treered_black_tree.hO(log N) insert, remove, and search
Sorted arraysorted_array.hO(N) insert/remove and O(log N) search
Splay treesplay_tree.hAmortized O(log N), worst-case O(N) per operation
Treaptreap.hExpected O(log N), worst-case O(N)

Benchmark methodology

The shared harness is in benchmark/benchmark_common.h. Each structure is tested at 1,000, 10,000, 20,000, 50,000, 100,000, and 200,000 elements.

The workloads are:

  • Random: insert a deterministic random permutation of 1..N.
  • Increasing: insert 1..N in sorted order.
  • Small shuffle: start with increasing values and shuffle values at 10% of the positions.
  • Remove: build from a random permutation, then remove all values in a different random order.
  • Search all: insert and search all N values; every search is a hit.
  • Small search, large insert: insert N values and search for N / 10 present values.
  • Large search, small insert: insert N / 10 values, then search N values; N / 10 searches are hits.

Input generation, structure setup for remove/search tests, and correctness validation are outside the timed regions. Only the operation loop is measured with std::chrono::steady_clock. Random inputs use fixed seeds, so the ordering is reproducible for a given size.

Recorded results

The following table summarizes the recorded results at N = 200,000. Times are milliseconds; lower is better. The fastest recorded time in each column is bold.

Data structureRandom insertIncreasing insertSmall-shuffle insertRemove allSearch allSearch 20K after insert 200KSearch 200K after insert 20K
AVL tree209.581125.422140.832193.09360.9784.49540.908
Binary heap49,268.17426,365.47146,907.01023,781.74649,491.5683,108.3335,866.317
Binary search tree100.05580,650.451109.87975.92566.7924.06855.263
Binary search trie135.79960.66466.421196.22568.5263.69258.553
Cuckoo hash table100.41346.97852.7217.0497.6730.9916.419
Hash table45.15634.26238.82446.4349.0570.9416.690
Linked list239,096.158189,989.965203,731.769149,494.633192,294.9341,556.71030,639.021
Red-black tree103.97682.44751.298150.76092.7339.01342.202
Sorted array16,057.89517.3081,814.58133,198.50157.1033.40436.153
Splay tree152.23438.27466.842238.230119.83420.30376.031
Treap212.08723.59562.130212.377137.7789.84144.332