Skip to content

Latest commit

 

History

History

README.md

📐 Architecture & Design Principles

The project follows a modular, decoupled architecture in .NET 10 designed for testability, performance analysis, and clean code practices:

  • Abstraction (ISortAlgorithm<T>): All sorting implementations implement a generic interface with the constraint where T : IComparable<T>, ensuring strict typing and support for any comparable data type (integers, strings, custom objects).
  • In-Place vs. Auxiliary Memory: Algorithms are implemented adhering to their theoretical spatial boundaries (e.g., $O(1)$ space for QuickSort/HeapSort, $O(N)$ auxiliary allocation for MergeSort).
  • Unit Testing (xUnit): Full coverage including edge cases (already sorted arrays, empty arrays, duplicate values, negative numbers, and string sorting).
  • Automated Benchmarking: Integrated with BenchmarkDotNet for precision CPU cycle profiling and Garbage Collector (MemoryDiagnoser) memory tracking.

📊 Performance Benchmarks

The benchmarks were executed under the following environment:

  • Tool: BenchmarkDotNet v0.15.8
  • Runtime: .NET 10.0 (X64 RyuJIT x86-64-v3)
  • Dataset: 1,000 randomly generated integers (N = 1000)

Results Summary

Method N Mean Error StdDev Gen0 Gen1 Allocated Memory
QuickSort 1000 16.43 µs 0.322 µs 0.501 µs 0.4578 - 3.93 KB
HeapSort 1000 26.82 µs 0.525 µs 0.769 µs 0.4578 - 3.93 KB
MergeSort 1000 36.85 µs 0.571 µs 0.445 µs 11.4746 0.1221 94.07 KB
BubbleSort 1000 1,677.34 µs 33.043 µs 62.868 µs - - 3.93 KB

Note: The baseline 3.93 KB allocation across all methods corresponds to the initial dataset clone required for isolated execution per iteration.

System Design Insights

  1. QuickSort (Top Performance - 16.43 µs): Outperformed all algorithms (~102x faster than BubbleSort). Its contiguous array partitioning maximizes CPU L1/L2 cache locality, minimizing cache misses.
  2. HeapSort (Guaranteed $O(1)$ Auxiliary Space - 26.82 µs): Achieved steady $O(N \log N)$ execution without incurring Garbage Collector overhead (0 GC collections), making it optimal for memory-constrained or real-time environments.
  3. MergeSort (Memory Trade-off - 36.85 µs & 94.07 KB Allocated): Demonstrated guaranteed $O(N \log N)$ stability, but required auxiliary array allocations during the merge phases, triggering Garbage Collector passes (Gen0/Gen1).
  4. BubbleSort (Baseline Comparison - 1.67 ms): Confirmed theoretical $O(N^2)$ quadratic degradation, serving as a baseline for algorithmic optimization.## 📐 Architecture & Design Principles

The project follows a modular, decoupled architecture in .NET 10 designed for testability, performance analysis, and clean code practices:

  • Abstraction (ISortAlgorithm<T>): All sorting implementations implement a generic interface with the constraint where T : IComparable<T>, ensuring strict typing and support for any comparable data type (integers, strings, custom objects).
  • In-Place vs. Auxiliary Memory: Algorithms are implemented adhering to their theoretical spatial boundaries (e.g., $O(1)$ space for QuickSort/HeapSort, $O(N)$ auxiliary allocation for MergeSort).
  • Unit Testing (xUnit): Full coverage including edge cases (already sorted arrays, empty arrays, duplicate values, negative numbers, and string sorting).
  • Automated Benchmarking: Integrated with BenchmarkDotNet for precision CPU cycle profiling and Garbage Collector (MemoryDiagnoser) memory tracking.

📊 Performance Benchmarks

The benchmarks were executed under the following environment:

  • Tool: BenchmarkDotNet v0.15.8
  • Runtime: .NET 10.0 (X64 RyuJIT x86-64-v3)
  • Dataset: 1,000 randomly generated integers (N = 1000)

Results Summary

Method N Mean Error StdDev Gen0 Gen1 Allocated Memory
QuickSort 1000 16.43 µs 0.322 µs 0.501 µs 0.4578 - 3.93 KB
HeapSort 1000 26.82 µs 0.525 µs 0.769 µs 0.4578 - 3.93 KB
MergeSort 1000 36.85 µs 0.571 µs 0.445 µs 11.4746 0.1221 94.07 KB
BubbleSort 1000 1,677.34 µs 33.043 µs 62.868 µs - - 3.93 KB

Note: The baseline 3.93 KB allocation across all methods corresponds to the initial dataset clone required for isolated execution per iteration.

System Design Insights

  1. QuickSort (Top Performance - 16.43 µs): Outperformed all algorithms (~102x faster than BubbleSort). Its contiguous array partitioning maximizes CPU L1/L2 cache locality, minimizing cache misses.
  2. HeapSort (Guaranteed $O(1)$ Auxiliary Space - 26.82 µs): Achieved steady $O(N \log N)$ execution without incurring Garbage Collector overhead (0 GC collections), making it optimal for memory-constrained or real-time environments.
  3. MergeSort (Memory Trade-off - 36.85 µs & 94.07 KB Allocated): Demonstrated guaranteed $O(N \log N)$ stability, but required auxiliary array allocations during the merge phases, triggering Garbage Collector passes (Gen0/Gen1).
  4. BubbleSort (Baseline Comparison - 1.67 ms): Confirmed theoretical $O(N^2)$ quadratic degradation, serving as a baseline for algorithmic optimization.