⚡️ Speed up method DiscreteDP.bellman_operator by 58%
#72
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
📄 58% (0.58x) speedup for
DiscreteDP.bellman_operatorinquantecon/markov/ddp.py⏱️ Runtime :
308 microseconds→196 microseconds(best of77runs)📝 Explanation and details
The optimization achieves a 57% speedup by replacing Python's dynamic dispatch with specialized Numba-compiled functions for different data structure types. Here's why this works:
Key Optimization: Specialized Numba Functions
The original code used a dynamically-defined closure
s_wise_maxthat dispatched to Numba-compiled helpers. This introduced Python function call overhead and prevented full optimization. The optimized version creates three specialized@njitfunctions:_bellman_operator_sa_pair- For sparse state-action pair formulation_bellman_operator_sa_pair_dense- For dense state-action pair formulation_bellman_operator_product- For product formulation (2D R, 3D Q)Why It's Faster
Static Dispatch: The
bellman_operatormethod now uses simpleif-elselogic to select the appropriate Numba function based onself._sa_pairandself._sparseflags. This eliminates the overhead of calling through the closure.Inlined Operations: Numba can now optimize the entire computation chain—from
vals = R + beta * (Q @ v)to the state-wise maximization—as a single compiled unit, enabling better register allocation and loop fusion.Reduced Python Interpreter Interaction: The hot loop that previously spent 96.2% of time in
s_wise_max(calling through Python) is now entirely within Numba-compiled code.Test Performance Patterns
Impact Assessment
Since
function_referencesis unavailable, we cannot definitively assess hot path usage. However, the Bellman operator is fundamental to dynamic programming solvers and typically called thousands of times in iterative algorithms (value iteration, policy iteration), making even small per-call speedups significant for cumulative performance.✅ Correctness verification report:
🌀 Click to see Generated Regression Tests
To edit these changes
git checkout codeflash/optimize-DiscreteDP.bellman_operator-mjw1i8pkand push.