BAM Operations#
Array operations for custom events.
This module provides NumPy-free operations for writing custom events, allowing economics researchers to work with BAM Engine without deep Python/NumPy knowledge.
Design Notes#
The operations mirror NumPy’s functionality but with:
Safe defaults: Division by zero prevention (eps=1e-10)
Consistent naming: Verb-based (multiply, divide vs * and /)
In-place operations: Support out= parameter for performance
Type hints: Better IDE support with Float, Int, Bool types
Operation Categories#
Arithmetic: add, subtract, multiply, divide
Comparisons: equal, less, greater, etc.
Logical: logical_and, logical_or, logical_not
Conditional: where (if-then-else)
Element-wise: maximum, minimum, clip
Aggregation: sum, mean, any, all
Array creation: zeros, ones, full, empty, arange, asarray, array
Mathematical: log, exp
Utilities: unique, bincount, isin, argsort, sort
Random: uniform (requires RNG)
Assignment: assign (in-place array modification)
Examples
Basic arithmetic operations:
>>> from bamengine import ops
>>> import numpy as np
>>> a = np.array([1.0, 2.0, 3.0])
>>> b = np.array([4.0, 5.0, 6.0])
>>> ops.add(a, b)
array([5., 7., 9.])
>>> ops.multiply(a, 2.0)
array([2., 4., 6.])
Safe division (handles zeros):
>>> wages = np.array([10.0, 12.0, 11.0])
>>> productivity = np.array([2.0, 3.0, 0.0]) # One zero!
>>> unit_cost = ops.divide(wages, productivity) # No error
>>> unit_cost[2] > 1e9 # Zero productivity handled
True
In-place operations for performance:
>>> out = np.zeros(3)
>>> result = ops.add(a, b, out=out)
>>> result is out # Same object
True
Conditional logic without NumPy:
>>> has_inventory = ops.greater(inventory, 0)
>>> new_price = ops.where(has_inventory, price * 0.95, price * 1.05)
Create a custom pricing event:
>>> from bamengine import event, ops
>>>
>>> @event
... class MarkupPricing:
... def execute(self, sim):
... prod = sim.get_role("Producer")
... emp = sim.get_role("Employer")
... # Calculate unit cost (safe division)
... unit_cost = ops.divide(emp.wage_offered, prod.labor_productivity)
... # Apply 20% markup
... new_prices = ops.multiply(unit_cost, 1.2)
... ops.assign(prod.price, new_prices)
Advanced Usage#
For users comfortable with NumPy, direct NumPy operations can be mixed with bamengine.ops for flexibility:
>>> import numpy as np
>>> # Mix ops and NumPy as needed
>>> from bamengine import event, ops
>>> @event
... class CustomEvent:
... def execute(self, sim):
... # Use ops for safety
... unit_cost = ops.divide(wages, productivity)
... log_prices = ops.log(prices)
... # Use NumPy directly for complex operations not in ops
... weighted_avg = np.average(prices, weights=market_share)
```
Arithmetic
Add two arrays or array and scalar. |
|
Subtract two arrays or array and scalar. |
|
Multiply two arrays or array and scalar. |
|
Divide two arrays or array and scalar (safe - avoids division by zero). |
Assignment
Assign value to target array (in-place operation). |
Comparisons
Element-wise equality comparison. |
|
Element-wise inequality comparison. |
|
Element-wise less than comparison. |
|
Element-wise less than or equal comparison. |
|
Element-wise greater than comparison. |
|
Element-wise greater than or equal comparison. |
Logical
Element-wise logical AND. |
|
Element-wise logical OR. |
|
Element-wise logical NOT. |
Conditional
Vectorized if-then-else (ternary operator). |
Element-wise
Element-wise maximum of array elements. |
|
Element-wise minimum of array elements. |
|
Clip (limit) values to range [min_val, max_val]. |
Aggregation
Sum array elements, optionally over axis or subset. |
|
Calculate mean, optionally over axis or subset. |
|
Calculate standard deviation, optionally over axis or subset. |
|
Return minimum value of array elements. |
|
Return maximum value of array elements. |
|
Test whether any array element is True. |
|
Test whether all array elements are True. |
Array creation
Create array of zeros. |
|
Create array of ones. |
|
Create array filled with constant value. |
|
Create uninitialized array (for performance when values will be overwritten). |
|
Create array with evenly spaced values within interval. |
|
Create a new numpy array from input data. |
|
Convert input to a numpy array. |
Mathematical
Utilities
Find unique elements in array. |
|
Count occurrences of each value in array of non-negative ints. |
|
Test whether each element is in test_elements. |
|
Return indices that would sort the array. |
|
Return sorted copy of array. |
Random
Draw samples from uniform distribution. |