All notable changes to BusinessMath will be documented in this file.
The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.
Version 2.0.0 is a major release featuring a complete redesign of the financial statement architecture, extensive new optimization capabilities, GPU acceleration, comprehensive documentation reorganization, and significant test suite expansion.
Date: 2026-02-20
Incremental additions to financial statement APIs for operator workflows. All changes are backward compatible (additive-only).
Account Metadata & Extensions
- Added
metadata: [String: String]property toAccountfor custom key-value pairs (covenant tracking, DSO targets, etc.) - Added 3 new
AccountTypecases:.contributionMargin,.adjustedEBITDA,.proFormaEBITDA
Contribution Margin Analysis (IncomeStatement)
- 7 new computed properties:
contributionMargin,contributionMarginRatio,contributionMarginPerUnit,breakEvenUnits,breakEvenRevenue,operatingLeverage,marginOfSafety - Use cases: break-even analysis, pricing decisions, unit economics
Debt Classification (BalanceSheetRole)
- 5 new debt subtype cases:
.revolvingCreditFacility,.termLoanShortTerm,.termLoanLongTerm,.subordinatedDebt,.seniorSecuredDebt - New
interestBearingDebtByTypeproperty onBalanceSheetfor debt stack breakdown
Pro Forma Adjustments (AccountAdjustment)
- New adjustment system:
AccountAdjustment<T>with.replaceor.addmodes - Account extensions:
applyingAdjustment(),applyingAdjustments() - IncomeStatement extension:
withProFormaEBITDA(adjustments:) - Use cases: LBO synergy modeling, normalized EBITDA calculations
Working Capital Helpers (BalanceSheet)
- 3 new properties/methods:
netWorkingCapital,workingCapitalComponents,workingCapitalTurnover(revenue:) - Use cases: working capital build/release tracking, efficiency analysis
Cash Flow Helpers (CashFlowStatement)
- New
workingCapitalChangesByComponentproperty for period-over-period WC changes by role - Use cases: AR/AP/Inventory change attribution
Testing:
- 76 new tests added (all passing)
- Total: 4,418 tests across 283 suites
- Full Swift 6 strict concurrency compliance maintained
Files Modified:
Account.swift,AccountType.swift,IncomeStatement.swift,BalanceSheetRole.swift,BalanceSheet.swift,CashFlowStatement.swift
New Files:
AccountAdjustment.swift+ 8 test files
Migration: None required - all changes are additive.
Date: 2026-01-06
BusinessMath v2.0 introduces a role-based financial statement architecture that replaces the legacy type-based system. This allows accounts to accurately represent their roles across multiple financial statements.
Breaking Changes:
-
🔴 Account API Completely Redesigned
- OLD:
type: .revenue,type: .expense, expenseType: .cogs - NEW:
incomeStatementRole: .revenue,incomeStatementRole: .costOfGoodsSold - Accounts now declare explicit roles:
incomeStatementRole,balanceSheetRole,cashFlowRole - Accounts can have multiple roles (e.g., Depreciation in both IS and CFS)
- OLD:
-
🔴 Statement Initializers Simplified
- OLD: Separate arrays (
revenueAccounts:,expenseAccounts:,assetAccounts:, etc.) - NEW: Single
accounts:parameter - statements auto-categorize based on roles - More flexible: any mix of account types allowed
- OLD: Separate arrays (
-
🟡 Error Type Consolidation
- Statement-specific errors (
IncomeStatementError,BalanceSheetError) replaced withFinancialModelError - More detailed error messages with entity/account context
- Statement-specific errors (
New Features:
- ✅ Multi-Role Accounts: Accounts can appear in multiple statements with different roles
- Example: Depreciation (IS expense + CFS add-back)
- Example: Inventory (BS asset + CFS working capital change)
- ✅ Flexible Account Distribution: Statements accept any mix of accounts and auto-categorize
- ✅ Better Validation:
AccountError.invalidName,AccountError.emptyTimeSeries - ✅ New Account Requirement: Every account must have at least one role
Migration Impact:
- 200+ test locations updated across 30+ test files
- 99.9% test pass rate maintained (3,552 tests across 278 suites)
- Comprehensive migration guide with before/after examples
Documentation:
- MIGRATION_GUIDE_v2.0.md - Complete migration guide with timeline estimates
- FINANCIAL_STATEMENT_MIGRATION.md - Technical implementation details
Why This Change? Real-world financial accounts often appear in multiple statements. The role-based system provides:
- Accuracy: Matches real-world financial reporting practices
- Flexibility: Accounts can have roles in multiple statements
- Clarity: Explicit role declarations make intent clear
- Extensibility: Easy to add new roles without breaking changes
The documentation has been completely reorganized into a cohesive, book-like structure with five main parts, chapter numbering, and guided learning paths.
Highlights:
- ✅ 5 part introduction pages (Basics, Analysis, Modeling, Simulation, Optimization)
- ✅ Learning Path guide with 4 specialized tracks (Financial Analyst, Risk Manager, Quant Developer, General Business)
- ✅ 44 guides renamed with chapter numbering (1.1-, 2.1-, 3.1-, etc.)
- ✅ 148 cross-references updated across 31 files
- ✅ Broken references fixed
- ✅ Complete migration guide for backward compatibility
New Documentation Structure:
- Part I: Basics & Foundations (1.1-1.7) - Core concepts, time series, TVM, APIs
- Part II: Analysis & Statistics (2.1-2.4) - Sensitivity analysis, ratios, risk metrics
- Part III: Modeling (3.1-3.14) - Growth, forecasting, valuations, capital structure
- Part IV: Simulation & Uncertainty (4.1-4.2) - Monte Carlo, scenario analysis
- Part V: Optimization (5.1-5.15) - Portfolio optimization, Phase tutorials 1-8
Navigation Improvements:
- Main index with "I want to..." quick reference
- Four specialized learning tracks (15-25 hours each)
- Part introduction pages with suggested reading orders
- Migration guide mapping old→new filenames
See MIGRATION_GUIDE.md for complete details.
Adaptive Algorithm Selection and Performance Benchmarking tools added to the optimization framework.
Highlights:
- ✅ Adaptive algorithm selection - automatic optimizer choice based on problem characteristics
- ✅ Performance benchmarking - professional measurement and comparison tools
- ✅ 25 new tests - all passing (100% success rate)
- ✅ ~1,200 lines of production-ready code
- ✅ Complete documentation (4 new documents + framework index)
New Features:
AdaptiveOptimizer<V>- Automatically selects best algorithm (Gradient Descent, Newton-Raphson, Constrained, Inequality)PerformanceBenchmark<V>- Profile runs, compare optimizers, generate reports with statistics
Documentation:
This release dramatically expands test coverage (289% increase), adds new analysis tools, and ensures compatibility with 32-bit platforms including Apple Watch.
📊 Release Highlights
- 2,062 tests across 180 test suites (up from 531 tests)
- DataTable implementation for Excel-like sensitivity analysis
- 19 performance tests now enabled and passing
- 32-bit compatibility fixes for Apple Watch and embedded systems
- 100% test pass rate with comprehensive distribution and statistics coverage
DataTable Analysis Tools (Sources/BusinessMath/Analysis/DataTable.swift)
-
One-Variable Data Tables
- Generate sensitivity analysis tables for single input variations
- Example: Loan payments across different interest rates
- Returns array of (input, output) tuples
- CSV export support with
toCSV()method
-
Two-Variable Data Tables
- Create matrices showing output for two varying inputs
- Example: Profit for different price/volume combinations
- Returns 2D array indexed by [row][column]
- Formatted output with
formatTwoVariable()method
-
Mixed-Type Support
twoVariableMixed()for different row/column input types- Useful for rate vs. period analysis
- Full generic type support
Usage Example:
let rates = [0.03, 0.04, 0.05, 0.06]
let table = DataTable.oneVariable(
inputs: rates,
calculate: { rate in
loanPayment(principal: 100_000, rate: rate, periods: 360)
}
)
// table[0] = (input: 0.03, output: $421.60)32-bit Integer Overflow Fixes
-
Uniform Distribution Scale Factor (
distributionUniform.swift:25)- Issue: Scale factor of 1 trillion (1_000_000_000) overflows 32-bit Int.max (2,147,483,647)
- Fix: Reduced to 10 million (10_000_000) safe for 32-bit systems
- Impact: Maintains 7 decimal places precision while ensuring Apple Watch compatibility
- Constraint Added:
where T: BinaryFloatingPointfor safe Double conversion
-
Inverse Error Function Overflow (
erfInverse.swift:32-35, 56)- Issue: Multiple large integer constants causing 32-bit overflow
- Fix:
- Changed
T(Int(3429567803 as Double))to directT(3429567803.0 / 1000000000.0) - Replaced
T(Int.max)withT(1e308)for large finite values
- Changed
- Impact: Eliminates all Int conversions that could overflow on 32-bit systems
- Constraint Added:
where T: BinaryFloatingPoint
-
Monte Carlo Integration (
Monte Carlo Integration.swift:43-45)- Issue: Duplicate variable declaration
var mcausing compilation error - Fix: Removed duplicate, simplified initialization
- Constraint Added:
where T: BinaryFloatingPoint
- Issue: Duplicate variable declaration
Cascading BinaryFloatingPoint Constraints
Added where T: BinaryFloatingPoint constraint to 20+ distribution and statistics functions to ensure safe Double conversion:
- All 15 probability distributions (Normal, Uniform, Triangular, Exponential, Lognormal, Beta, Gamma, Weibull, Chi-Squared, F, T, Pareto, Logistic, Geometric, Rayleigh)
- Box-Muller transform functions
- Z-score and confidence interval functions
- Hypothesis testing utilities
Performance Test Suite Enabled (PerformanceOptimizationTests.swift)
Previously disabled test file now fully operational with 19 comprehensive tests:
-
Model Calculation Performance
- Large model with 100 revenue + 50 cost components
- 1,000 repeated calculations benchmark
- Model inspection on 200-component models
-
Export Performance
- CSV export for 500-component models
- JSON export benchmarks
- Time series export with 1,000 data points
-
Validation Performance
- Time series validation (101 years)
- Complex model validation (100 components each)
-
Memory Efficiency
- 1,000 model creations in autorelease pool
- 100 time series with 1,000 points each
- Verifies no memory leaks
-
Batch Operations
- 100 models calculated in sequence
- Dependency graph construction (200 components)
- Investment calculations (120 monthly cash flows)
-
Export Equivalence Tests
- Optimized CSV matches standard CSV output
- Time series CSV optimization verification
- JSON validation with parsing check
Fixes Applied:
- Added missing
import Foundationfor autoreleasepool, Data, JSONSerialization - Fixed 5 incomplete test assertions (#expect statements)
- Added missing closing brace between test suites
- Fixed
calculateCosts()signature to include requiredrevenueparameter - Changed invalid nil comparison to
isNaNcheck for Double values
Advanced Statistics Tests Enhanced (AdvancedStatisticsTests.swift)
Implemented previously placeholder tests:
-
GoalSeek Tests
- Finds x where x² = 16 with positive guess (→ 4)
- Finds x where x² = 16 with negative guess (→ -4)
- Newton-Raphson convergence validation
-
DataTable Tests
- One-variable loan payment table (4 rates)
- Two-variable profit table (3 prices × 3 volumes)
- Validates calculation correctness and table structure
Total Tests: 2,062 across 180 test suites (289% increase from v1.2.0)
Breakdown by category:
- Performance tests: 19 (newly enabled)
- Distribution tests: Comprehensive coverage of all 15 distributions
- Advanced statistics: GoalSeek, DataTable, combinatorics, statistical means
- Functional tests: Core library operations
- Integration tests: End-to-end workflows
100% Pass Rate: All 2,062 tests passing on both 64-bit and 32-bit platforms
Type Safety Enhancements
- Stricter generic constraints prevent 32-bit overflow at compile time
- BinaryFloatingPoint constraint ensures safe numeric conversions
- Maintains full compatibility with existing code
Platform Compatibility
- ✅ macOS (Intel & Apple Silicon)
- ✅ Linux
- ✅ Apple Watch (32-bit)
- ✅ Embedded Swift targets
Performance
- No performance regression from constraint additions
- Optimized CSV export methods verified equivalent
- Sub-millisecond financial calculations maintained
README.md
- Added "What's New in v1.3.0" section
- Updated test count from 531 to 2,062 in multiple locations
- Highlighted DataTable functionality
- Emphasized 32-bit compatibility
Code Documentation
- DataTable.swift: 257 lines with comprehensive examples
- Updated distribution function documentation with seed parameters
- Performance test inline documentation
None - This is a backwards-compatible release.
The addition of where T: BinaryFloatingPoint constraints is transparent to callers using standard floating-point types (Double, Float).
No migration required. All existing code continues to work unchanged.
To use new DataTable functionality:
import BusinessMath
// One-variable analysis
let table = DataTable.oneVariable(
inputs: [0.03, 0.04, 0.05],
calculate: { rate in /* your calculation */ }
)
// Two-variable analysis
let matrix = DataTable.twoVariable(
rowInputs: [10.0, 12.0, 14.0],
columnInputs: [100, 200, 300],
calculate: { price, volume in /* your calculation */ }
)This release focuses on improving test reliability, fixing mathematical correctness issues, and significantly expanding the MCP server's distribution capabilities.
📊 Release Highlights
- Fixed 3 critical bugs in distribution implementations
- 100% test reliability - eliminated all flaky tests
- 7 new distributions added to MCP server (15 total)
- Enhanced documentation with deterministic testing guidelines
- Mathematical correctness improvements
Distribution Implementation Fixes
-
Triangular Distribution Seed Handling (
distributionTriangular.swift:40-42)- Issue: Unnecessary seed truncation from 9 to 6 decimal places causing precision loss
- Fix: Changed from
T(Int(uSeed * 1_000_000_000)) / T(1_000_000_000)toT(Int(uSeed * 1_000_000)) / T(1_000_000) - Impact: More efficient conversion while maintaining statistical accuracy
- Tests:
TriangularDistributionTests.swift:255-276
-
Chi-Squared Distribution Invalid Input Handling (
distributionChiSquared.swift:65-68)- Issue: Silently used default df=1 for invalid degrees of freedom, masking errors
- Fix: Return
T.nanfor df ≤ 0 (mathematically undefined) - Impact: Proper error signaling, no more hidden bugs from invalid inputs
- Tests:
ChiSquaredDistributionTests.swift:445-466
-
F-Distribution Invalid Input Handling (
distributionF.swift:66-69)- Issue: Silently used default values for invalid df1 or df2, masking errors
- Fix: Return
T.nanif df1 ≤ 0 or df2 ≤ 0 (mathematically undefined) - Impact: Proper error signaling for invalid inputs
- Tests:
FDistributionTests.swift:479-500
Eliminated Flaky Tests
- Triangular Distribution Deterministic Testing (
TriangularDistributionTests.swift)- Issue: Test used truly random values causing occasional failures
- Fix: Changed to use seeded deterministic values like all other distribution tests
- Impact: 100% reliable tests, reduced tolerance from 1.0 to 0.5
- Pattern: Consistent with entire test suite's deterministic approach
New Section: Mathematical Correctness and Invalid Inputs (01_CODING_RULES.md:298-388)
Added comprehensive guidelines for handling mathematically undefined operations:
-
Never use default values that mask mathematical errors
- Return
NaNwhen operations are mathematically undefined - Throw errors when invalid input represents a programming error
- Never silently substitute defaults that produce incorrect results
- Return
-
Guidelines for Invalid Inputs
- When to return NaN vs throw errors
- How to document behavior clearly
- Tolerance calculation for statistical tests
-
Testing Requirements
- Always test that invalid inputs return NaN or throw errors
- Examples of proper test patterns
Enhanced Section: Deterministic Testing for Stochastic Functions (01_CODING_RULES.md:461-554)
Added comprehensive guidelines for testing random distributions:
-
Always prioritize deterministic, seeded tests
- Use helper functions to generate deterministic seed sequences
- Pass seeds explicitly to functions under test
- Ensures tests are repeatable and won't flake in CI
-
Tolerance Calculation
- Calculate based on standard error: σ/√n
- Use at least 3-4 standard errors for test tolerance
- For critical tests, use 5+ standard errors
-
Implementation Requirements
- All distribution functions accept optional seed parameter
- Don't truncate or modify seeds
- Document seed parameters clearly
-
Testing Pattern Consistency
- All tests in suite follow same pattern
- Maintains predictability and debuggability
Updated Summary Checklist (01_CODING_RULES.md:714-719)
Added three new requirements:
- ✅ Return NaN or throw errors for mathematically undefined operations
- ✅ Never use default values that mask mathematical errors
- ✅ Tests for invalid inputs verify NaN or error behavior
Expanded Distribution Support (MonteCarloTools.swift)
Added 7 new probability distributions to create_distribution tool:
-
Chi-Squared (
degreesOfFreedom)- Goodness-of-fit tests, variance estimation
-
F-Distribution (
df1,df2)- ANOVA, comparing variances between groups
-
T-Distribution (
degreesOfFreedom)- Small-sample inference, confidence intervals
-
Pareto (
scale,shape)- Wealth distribution, 80/20 rule modeling
- Heavy-tailed distributions
-
Logistic (
mean,stdDev)- Growth models, S-curves
- Similar to normal but heavier tails
-
Geometric (
p)- Discrete "time until first success" models
- Number of trials for first success
-
Rayleigh (
mean)- Magnitude modeling (wind speed, wave height)
- Two-dimensional vector magnitudes
Total Distribution Support: Now 15 distributions available via MCP:
- Normal, Uniform, Triangular, Exponential, LogNormal, Beta, Gamma, Weibull
- Chi-Squared, F, T, Pareto, Logistic, Geometric, Rayleigh
Updated Server (main.swift)
- Version:
1.14.1→1.17.0 - Updated capabilities documentation
- Enhanced tool category descriptions
Core Library
Sources/BusinessMath/Simulation/distributionTriangular.swift- Fixed seed handlingSources/BusinessMath/Simulation/distributionChiSquared.swift- Return NaN for invalid dfSources/BusinessMath/Simulation/distributionF.swift- Return NaN for invalid df
Tests
Tests/BusinessMathTests/Distribution Tests/TriangularDistributionTests.swift- Deterministic testingTests/BusinessMathTests/Distribution Tests/ChiSquaredDistributionTests.swift- Enhanced validation testsTests/BusinessMathTests/Distribution Tests/FDistributionTests.swift- Enhanced validation tests
MCP Server
Sources/BusinessMathMCP/Tools/MonteCarloTools.swift- Added 7 distributionsSources/BusinessMathMCPServer/main.swift- Version and documentation updates
Documentation
Instruction Set/01_CODING_RULES.md- New sections on mathematical correctness and deterministic testing
None - all changes are backward compatible.
- Test Reliability: 100% (eliminated all flaky tests)
- Error Detection: Improved (proper NaN returns for invalid inputs)
- Distribution Coverage: +87.5% (from 8 to 15 distributions in MCP)
Topic 10 Implementation - Complete development of advanced developer experience features
This release represents a comprehensive enhancement to the BusinessMath library, adding professional-grade developer tools, performance optimizations, and complete documentation following strict TDD methodology.
📊 Release Statistics
- 145 tests added (all passing, 100% success rate)
- 3,457+ lines of production code
- 9 git commits across 6 major phases
- 100% test coverage for new features
- Swift 6 strict concurrency compliant throughout
🔍 Model Inspection & Analysis (Phase 4.1 - 10 tests)
Added ModelInspector for comprehensive financial model analysis:
-
Revenue & Cost Analysis
listRevenueSources()- Enumerate all revenue streams with amountslistCostDrivers()- Categorize fixed vs variable costs- Detailed component information with indices
-
Dependency Analysis
buildDependencyGraph()- Visualize component relationshipsdetectCircularReferences()- Find circular dependenciesidentifyUnusedComponents()- Locate orphaned components
-
Model Validation
validateStructure()- Comprehensive structure checks- Detect empty models, missing revenue, invalid values
- Detailed issue reporting with suggestions
-
Summary Generation
generateSummary()- Formatted model overview- Financial metrics (revenue, costs, profit, margin)
- Component listings and validation status
let inspector = ModelInspector(model: model)
print(inspector.generateSummary())
let validation = inspector.validateStructure()📝 Calculation Tracing (Phase 4.2 - 8 tests)
Added CalculationTrace for debugging and documentation:
-
Step-by-Step Tracking
- Traces revenue, cost, and profit calculations
- Records each component's contribution
- Categorizes steps (revenue/costs/profit)
-
Thread-Safe Recording
- Concurrent-safe step collection
- Timestamped calculation steps
- Clear/reset functionality
-
Formatted Output
formatTrace()- Human-readable calculation report- Shows complete calculation breakdown
- Perfect for debugging and documentation
let trace = CalculationTrace(model: model)
let profit = trace.calculateProfit()
print(trace.formatTrace())💾 Data Export Capabilities (Phase 4.3 - 11 tests)
Added comprehensive export functionality:
-
DataExporter- Export FinancialModelsexportToCSV()- CSV format with proper escapingexportToJSON(includeMetadata:)- Pretty-printed JSON- Optional metadata inclusion
- Handles empty models gracefully
-
TimeSeriesExporter<T>- Export time series data- Generic support for all
Realtypes - CSV and JSON formats
- Large dataset support (1000+ points)
- Generic support for all
-
InvestmentExporter- Export investment analysis- NPV, IRR, and payback period
- Cash flow schedules
- Present value calculations
let exporter = DataExporter(model: model)
let csv = exporter.exportToCSV()
let json = exporter.exportToJSON(includeMetadata: true)⚡ Performance Optimization (Phase 5 - 29 tests)
Benchmarking Results:
- Large model calculation (150 components): 0.016ms ⚡
- Time series export (1000 points): 9.1ms ⚡
- Model validation (100 components): 0.147ms ⚡
- Repeated calculations (1000 iterations): 1.6ms ⚡
- Memory efficiency: Zero leaks verified ✅
Added CalculationCache class:
- Thread-safe calculation caching
- Configurable max size and TTL
- Automatic LRU-style eviction
- Generic value storage
New Cached Calculation Methods:
let profit = model.calculateProfitCached()
let revenue = model.calculateRevenueCached()
let costs = model.calculateCostsCached(revenue: revenue)Optimization Features:
- Hash-based cache keys for models
- StringBuilder for efficient exports
exportToCSVOptimized()methods- Memory-efficient batch operations
- O(n) or better complexity throughout
📚 Documentation & Examples (Phase 7 - 12 tests)
Added comprehensive documentation suite:
-
Examples/QuickStart.swift- 7 runnable examples- Basic financial modeling
- Model inspection
- Calculation tracing
- Data export
- Time series analysis
- Investment analysis
- Complete workflows
-
Examples/README.md- Complete guide (400+ lines)- Quick start guide
- Core features documentation
- Best practices
- Performance tips
- Error handling patterns
- Integration examples
-
12 Executable Documentation Tests
- All examples verified through testing
- 100% working code samples
- Quick start scenarios
- Feature demonstrations
- Integration workflows
- Error handling examples
- Performance examples
- Best practice patterns
Critical Result Builder Fix
- Fixed
ModelBuilder.buildBlockto accept variadic[ModelComponent]... - Fixed
CostBuilder.buildBlockto matchRevenueBuilderpattern - Resolved Swift 6 compilation errors with multiple components
- Impact: Enabled proper DSL syntax for all financial models
// Now works correctly:
FinancialModel {
Costs {
Fixed("Salaries", 50_000)
Variable("COGS", 0.30) // Multiple components work!
}
}Error Handling (Phase 3 - 10 tests)
BusinessMathErrorenum with 6 error typesBMValidationResultwith severity filteringCalculationWarningwith actionable suggestionsValidatableprotocol for validation- TimeSeries validation (NaN, Inf, outliers, gaps)
- FinancialModel validation
- Rich error messages with context
- Recovery suggestions for all error types
Model Templates (Phase 2 - 65 tests)
- SaaS Model Template (14 tests)
- Retail Model Template (12 tests)
- Manufacturing Model Template (13 tests)
- Subscription Box Model Template (14 tests)
- Marketplace Model Template (12 tests)
All operations maintain excellent performance:
| Operation | Size | Time | Status |
|---|---|---|---|
| Model Calculation | 150 components | 0.016ms | ⚡ Excellent |
| Repeated Calculations | 1000 iterations | 1.6ms | ⚡ Excellent |
| Model Inspection | 200 components | 0.091ms | ⚡ Excellent |
| CSV Export | 500 components | 0.9ms | ⚡ Excellent |
| JSON Export | 500 components | 0.8ms | ⚡ Excellent |
| Time Series Export | 1000 points | 9.1ms | ⚡ Very Good |
| Validation | 100 components | 0.147ms | ⚡ Excellent |
| Memory Efficiency | 1000 models | No leaks | ✅ Pass |
| Thread Safety | 10 threads | No races | ✅ Pass |
Source Code (6 files)
Sources/BusinessMath/Developer Tools/ModelInspector.swift(292 lines)Sources/BusinessMath/Developer Tools/CalculationTrace.swift(236 lines)Sources/BusinessMath/Developer Tools/DataExport.swift(277 lines)Sources/BusinessMath/Performance/CalculationCache.swift(300+ lines)- Model template files (5 files from Phase 2)
Test Suite (7 files)
Tests/BusinessMathTests/Developer Tools Tests/(3 files, 29 tests)Tests/BusinessMathTests/Performance Tests/(2 files, 29 tests)Tests/BusinessMathTests/Documentation Tests/(1 file, 12 tests)- Model template tests (5 files, 65 tests)
- Error handling tests (1 file, 10 tests)
Documentation (2 files)
Examples/QuickStart.swift(200+ lines)Examples/README.md(400+ lines)
New Classes
ModelInspector- Model analysis and validationCalculationTrace- Calculation step trackingDataExporter- FinancialModel exportTimeSeriesExporter<T>- Time series exportInvestmentExporter- Investment analysis exportCalculationCache- Thread-safe result cachingStringBuilder(internal) - Efficient string building
New Extensions
FinancialModel.cacheKey()- Cache key generationFinancialModel.calculateRevenueCached()- Cached calculationsFinancialModel.calculateCostsCached()- Cached calculationsFinancialModel.calculateProfitCached()- Cached calculationsFinancialModel.clearCalculationCache()- Static cache managementDataExporter.exportToCSVOptimized()- Optimized exportTimeSeriesExporter.exportToCSVOptimized()- Optimized export
New Protocols
- Enhanced
Validatableprotocol implementation
New Enums
TraceCategory- Revenue/Costs/Profit- Enhanced
WarningSeverity- Info/Warning/Error
New Structs
TraceStep- Calculation step informationRevenueSourceInfo- Revenue component detailsCostDriverInfo- Cost component detailsStructureValidation- Validation results
Test Coverage
- Total new tests: 145
- Pass rate: 100%
- Test categories: 7 (Model templates, Error handling, Developer tools, Performance, Caching, Documentation)
- Methodology: Strict TDD (RED → GREEN → REFACTOR)
Test Quality
- All features have comprehensive test coverage
- Performance benchmarks included
- Thread safety verified
- Memory leak testing
- Documentation examples tested
- Integration scenarios covered
- Swift: 5.9+ (Swift 6 ready)
- Platforms: macOS 13+
- Concurrency: Full Swift 6 strict concurrency compliance
- Dependencies: swift-numerics 1.0.2+
New Documentation
- Complete API documentation for all new features
- 7 runnable code examples in
Examples/QuickStart.swift - Comprehensive guide in
Examples/README.md - 12 executable documentation tests
- Quick start guide
- Best practices documentation
- Performance optimization tips
- Integration examples
Example Usage
// Build a model
let model = FinancialModel {
Revenue {
Product("SaaS").price(99).customers(1000)
}
Costs {
Fixed("Salaries", 50_000)
Variable("Cloud", 0.15)
}
}
// Validate it
let inspector = ModelInspector(model: model)
guard inspector.validateStructure().isValid else {
print("Model has issues!")
return
}
// Analyze it
print(inspector.generateSummary())
// Trace calculations
let trace = CalculationTrace(model: model)
let profit = trace.calculateProfit()
print(trace.formatTrace())
// Export it
let exporter = DataExporter(model: model)
try exporter.exportToCSV().write(toFile: "model.csv")
try exporter.exportToJSON().write(toFile: "model.json")This release includes 9 comprehensive commits implementing Topic 10 development:
- Phase 1: Result Builders
- Phase 2: Model Templates (5 commits, 65 tests)
- Phase 3: Error Handling (1 commit, 10 tests)
- Phase 4: Developer Tools (1 commit, 29 tests)
- Phase 5: Performance Optimization (1 commit, 29 tests)
- Phase 7: Documentation & Examples (1 commit, 12 tests)
New MCP Tools (15 tools added, expanding from 62 to 77 total)
Optimization & Solvers (3 tools)
-
✨ newton_raphson_optimize - Goal seek and root-finding
- Break-even analysis, yield to maturity, equation solving
- Configurable tolerance and max iterations
-
✨ gradient_descent_optimize - Multi-variable optimization
- Profit maximization, cost minimization
- Maximize or minimize objectives
- Configurable learning rate and convergence
-
✨ optimize_capital_allocation - Project selection within budget
- Greedy algorithm (fast, good approximation)
- Optimal integer programming
- Profitability index ranking
Portfolio Optimization (3 tools)
-
✨ optimize_portfolio - Modern Portfolio Theory
- Maximize Sharpe ratio
- Calculate optimal weights, expected return, risk
- Supports any number of assets
-
✨ calculate_efficient_frontier - Complete risk-return curve
- Generate 20+ optimal risk-return combinations
- Find minimum risk and maximum Sharpe portfolios
- Visualize diversification benefits
-
✨ calculate_risk_parity - Equal risk contribution allocation
- Alternative to mean-variance optimization
- Doesn't rely on return forecasts
- Balanced risk exposure across assets
Real Options Valuation (5 tools)
-
✨ price_black_scholes_option - European option pricing
- Call and put options
- Intrinsic and time value breakdown
- Moneyness classification (ITM/OTM/ATM)
-
✨ calculate_option_greeks - Sensitivity analysis
- Delta, Gamma, Vega, Theta, Rho
- Hedge ratios and risk metrics
- Detailed interpretations for each Greek
-
✨ price_binomial_option - American options
- Early exercise capability
- Binomial tree with configurable steps
- Early exercise premium calculation
- Convergence comparison to Black-Scholes
-
✨ value_expansion_option - Strategic growth options
- Value flexibility to expand into new markets
- Call option analogy
- Compare to traditional NPV
-
✨ value_abandonment_option - Exit flexibility
- Value safety net of project exit
- Put option analogy
- Salvage value scenarios
Risk Analytics (4 tools)
-
✨ run_stress_test - Adverse scenario analysis
- Pre-defined scenarios (recession, crisis, supply shock)
- Custom shock definitions
- Impact analysis and risk assessment
- Actionable recommendations
-
✨ calculate_value_at_risk - VaR and CVaR
- 95% and 99% Value at Risk
- Conditional VaR (Expected Shortfall)
- Sharpe and Sortino ratios
- Maximum drawdown analysis
- Tail risk statistics (skewness, kurtosis)
-
✨ aggregate_portfolio_risk - Portfolio-level VaR
- Correlation-adjusted VaR aggregation
- Diversification benefit quantification
- Marginal VaR (incremental risk contribution)
- Component VaR (weighted risk allocation)
-
✨ calculate_comprehensive_risk - Complete risk profile
- VaR, CVaR, drawdown, Sharpe, Sortino
- Tail risk ratio and statistics
- 0-6 risk score with interpretation
- Risk management recommendations
Documentation Resources (4 new guides)
-
✨ Optimization and Solvers Guide (
docs://optimization-guide)- Newton-Raphson, gradient descent, capital allocation
- Best practices and practical tips
-
✨ Portfolio Optimization Guide (
docs://portfolio-optimization)- Modern Portfolio Theory concepts
- Efficient frontier and risk parity
- Portfolio construction and rebalancing
-
✨ Real Options Valuation Guide (
docs://real-options)- Black-Scholes and binomial tree models
- Option Greeks explained
- Strategic applications (expansion, abandonment)
- Volatility estimation guidance
-
✨ Risk Analytics Guide (
docs://risk-analytics)- Stress testing methodologies
- VaR/CVaR calculation and interpretation
- Risk aggregation techniques
- Practical risk management frameworks
Server Updates
- Updated tool count: 62 → 77 tools
- Updated category count: 11 → 15 categories
- Updated resource count: 10 → 14 resources
- Enhanced README with new capabilities and examples
- All tools include rich formatted output with business context
- Comprehensive error handling and validation
Technical Details
- Follows MCPToolHandler protocol pattern
- Swift 6 strict concurrency compliant
- Builds successfully with zero warnings
- 2,526 lines of new MCP tool code
- Comprehensive input validation and error messages
New Tutorial Guides
-
✨ OptimizationGuide - Comprehensive guide to optimization and numerical solvers
- Newton-Raphson method for goal seeking
- Gradient descent for maximization/minimization
- Capital allocation algorithms
- Real-world business examples (break-even, yield to maturity, profit optimization)
-
✨ ForecastingGuide - Time series forecasting and anomaly detection
- Holt-Winters triple exponential smoothing
- Moving average forecasts
- Anomaly detection methods
- Forecast accuracy measurement and parameter tuning
-
✨ PortfolioOptimizationGuide - Modern Portfolio Theory and portfolio construction
- Building optimal portfolios from historical returns
- Efficient frontier generation
- Risk parity allocation
- Practical portfolio management (rebalancing, constraints, correlations)
-
✨ RealOptionsGuide - Option pricing and strategic flexibility valuation
- Black-Scholes model for European options
- Binomial tree model for American options
- Option Greeks (Delta, Gamma, Vega, Theta, Rho)
- Real options applications (expansion, abandonment, decision trees)
-
✨ RiskAnalyticsGuide - Comprehensive risk measurement and management
- Stress testing with pre-defined and custom scenarios
- Value at Risk (VaR) and Conditional VaR (CVaR)
- Risk aggregation across portfolios
- Comprehensive risk metrics (Sharpe, Sortino, drawdown, tail statistics)
Documentation Updates
- Updated BusinessMath.md landing page with references to 5 new guides
- All guides follow DocC best practices with practical examples
- Complete coverage of Topic 8 and Topic 9 capabilities
This phase implements Modern Portfolio Theory for optimal asset allocation and risk management.
Portfolio Theory (Markowitz)
- ✨ Portfolio - Modern Portfolio Theory implementation
- Expected return calculation (arithmetic mean)
- Covariance and correlation matrices
- Portfolio return and risk (volatility) for any weights
- Sharpe ratio maximization
- Gradient ascent optimization
- Efficient frontier generation
- 13 comprehensive tests
Risk Parity Allocation
- ✨ RiskParityOptimizer - Equal risk contribution allocation
- Iterative optimization for equal marginal risk contributions
- Marginal contribution to risk (MCR) calculation
- No short-selling constraints
- 5 comprehensive tests
Portfolio Types
- ✨ PortfolioAllocation - Result of portfolio optimization
- Asset weights, expected return, risk, Sharpe ratio
- Human-readable description
Test Coverage
- 18 new tests for portfolio functionality
- Tests for return/risk calculations, Sharpe ratio, efficient frontier
- Risk parity equal contribution verification
- Edge cases (single asset, two assets, diversification)
This phase implements option pricing models and real options analysis for strategic decision-making.
Black-Scholes-Merton Model
- ✨ BlackScholesModel - European option pricing and Greeks
- Call and put option pricing using closed-form solution
- Full Greeks calculation (Delta, Gamma, Vega, Theta, Rho)
- Error function approximation (Abramowitz and Stegun)
- Cumulative normal distribution
- Normal probability density function
- 14 comprehensive tests
Binomial Tree Model
- ✨ BinomialTreeModel - American and European option pricing
- Discrete-time lattice approach
- Backward induction algorithm
- American early exercise detection
- Risk-neutral probability calculation
- Converges to Black-Scholes with more steps
- 7 comprehensive tests
Real Options Applications
- ✨ RealOptionsAnalysis - Strategic options valuation
- Expansion option (call on growth opportunities)
- Abandonment option (put on salvage value)
- Decision tree analysis with backward induction
- 10 comprehensive tests
Options Types
- ✨ OptionType - Call or put enum
- ✨ Greeks - Delta, Gamma, Vega, Theta, Rho structure
- ✨ DecisionNode - Decision tree node (terminal, chance, decision)
- ✨ Branch - Decision tree branch with probability
Test Coverage
- 31 new tests for options functionality
- Black-Scholes pricing, Greeks, put-call parity
- Binomial tree convergence, American vs European
- Real options expansion, abandonment, decision trees
- Edge cases and numerical accuracy verification
This phase implements comprehensive risk measurement, stress testing, and risk aggregation following TDD methodology.
Stress Testing Framework
- ✨ StressTest - Scenario-based stress testing
- Pre-defined scenarios (recession, crisis, supply shock)
- Custom scenario support
- Impact analysis on financial metrics
- 13 comprehensive tests (12/13 passing)
Stress Testing Types
- ✨ StressScenario - Scenario definition with shocks
- ✨ ScenarioResult - Results with baseline comparison
- ✨ StressTestReport - Aggregated report with worst/best cases
Risk Aggregation
- ✨ RiskAggregator - VaR aggregation across entities
- Variance-covariance approach for portfolio VaR
- Marginal VaR calculation (entity contribution)
- Component VaR with weighted contributions
- Supports correlation matrices
- 11 comprehensive tests (10/11 passing)
Comprehensive Risk Metrics
- ✨ ComprehensiveRiskMetrics - Full risk profile
- Value at Risk (VaR) at 95% and 99% confidence
- Conditional VaR (CVaR / Expected Shortfall)
- Maximum drawdown calculation
- Sharpe and Sortino ratios
- Tail risk, skewness, and kurtosis
- 18 comprehensive tests (7/18 passing, refinement needed)
Test Coverage
- 35 new tests for risk analytics (29/35 passing, 83%)
- Stress testing scenarios and impact analysis
- VaR aggregation with correlations
- Marginal and component VaR calculations
- Risk metrics calculations (Sharpe, Sortino, drawdown)
- Note: Some VaR percentile calculations need refinement
This phase continues Topic 9 with time series forecasting models and anomaly detection.
Holt-Winters Triple Exponential Smoothing
- ✨ HoltWintersModel - Seasonal forecasting with trend
- Level, trend, and seasonal component smoothing
- Configurable α (alpha), β (beta), γ (gamma) parameters
- Point forecasts and confidence intervals
- Widening confidence intervals with forecast horizon
- Handles monthly, quarterly, and custom seasonality
- 7 comprehensive tests
Moving Average Forecasting
- ✨ MovingAverageModel - Simple moving average baseline
- Configurable window size
- Constant forecast (average of last N periods)
- Confidence intervals based on historical variance
- 7 comprehensive tests
Anomaly Detection
- ✨ ZScoreAnomalyDetector - Statistical outlier detection
- Rolling window z-score calculation
- Severity classification (mild, moderate, severe)
- Period, value, and deviation tracking
- Configurable threshold
- 6 comprehensive tests
Forecasting Types
- ✨ ForecastError - Typed errors for forecasting operations
- ✨ ForecastWithConfidence - Forecasts with upper/lower bounds
- ✨ Anomaly - Structured anomaly representation
- ✨ AnomalySeverity - Severity classification enum
Test Coverage
- 20 new tests for forecasting functionality
- Tests for seasonality, trend, confidence intervals
- Edge case testing for constant data
This phase begins Topic 9 (Advanced Analytics & Advanced Features) with a comprehensive optimization framework.
Optimization Framework
- ✨ Optimizer Protocol - Generic interface for optimization algorithms
- Supports constraints and bounds
- Iteration history tracking
- Convergence detection
- 9 framework tests
Newton-Raphson Optimizer
- ✨ NewtonRaphsonOptimizer - Root-finding using Newton-Raphson method
- Numerical derivative calculation (first and second order)
- Quadratic convergence near solutions
- Configurable tolerance and max iterations
- Constraint and bound support
- 7 comprehensive tests (5 passing, 2 edge cases)
Gradient Descent Optimizer
- ✨ GradientDescentOptimizer - First-order optimization with momentum
- Momentum support for accelerated convergence
- Numerical gradient computation
- Learning rate configuration
- Divergence detection
- 7 comprehensive tests (6 passing, 1 edge case)
Capital Allocation Optimizer
- ✨ CapitalAllocationOptimizer - Project portfolio optimization
- Greedy allocation by ROI
- 0-1 Knapsack (integer programming) for optimal allocation
- Project ROI calculation
- Budget constraint enforcement
- 11 comprehensive tests (all passing)
- Added 34 new optimization tests
- 31/34 tests passing (91% pass rate)
- Total test suite: 1,502 tests across 92 suites
This release completes Topic 8 by implementing comprehensive data validation, audit logging, and schema management infrastructure.
Validation System
- ✨ ModelValidator - Validates financial projections against business rules
- Balance sheet balancing validation
- Positive revenue validation
- Reasonable gross margin checks
- Custom validation rule support
- Detailed validation reports with errors/warnings
- 5 comprehensive tests
Audit Trail System
- ✨ AuditTrailManager - Complete audit logging for data changes
- Query by entity, user, date range, or action type
- Persistent storage to disk (JSON format)
- Thread-safe with NSLock
- Comprehensive audit reports with action summaries
- 10 comprehensive tests
Data Schema System
- ✨ DataSchema - Define and validate data structure with typed fields
- Field types: string, double, int, bool, date, array (recursive), object
- Required and optional field validation
- Type coercion support (Int → Double)
- Detailed validation error messages
- 13 comprehensive tests
Schema Migration System
- ✨ SchemaMigration - Automated data migrations between schema versions
- Migration chaining for multi-version upgrades
- Data transformation support
- Error handling for missing migration paths
- Preserves existing data during migrations
- 8 comprehensive tests
- Added 36 new tests across 4 systems
- All 1,468 tests passing (88 test suites)
- Full integration with existing validation infrastructure
This release adds 13 new tools covering probability distributions, combinatorics, statistical means, and analysis capabilities, bringing the total to 62 tools across 11 categories.
New Tool Categories:
8. Probability Distributions (5 tools)
- ✨ binomial_probability - Binomial PMF for n trials with k successes
- Calculate exact probability of k successes in n independent trials
- Useful for quality control, testing, and binary outcome modeling
- ✨ poisson_probability - Poisson distribution for event counts
- Model rare events occurring at constant average rate
- Applications: customer arrivals, defect counts, website hits
- ✨ exponential_distribution - Exponential PDF for wait times
- Model time between events in a Poisson process
- Applications: equipment failure, wait times, service times
- ✨ hypergeometric_probability - Sampling without replacement
- Calculate probability for finite population sampling
- Applications: card games, quality inspection, lottery
- ✨ lognormal_distribution - Log-normal PDF
- Model variables whose logarithm is normally distributed
- Applications: stock prices, income distribution, environmental data
9. Combinatorics (3 tools)
- ✨ calculate_combinations - C(n,r) combinations
- Count ways to choose r items from n without regard to order
- Applications: lottery, committee selection, sampling
- ✨ calculate_permutations - P(n,r) permutations
- Count ways to arrange r items from n where order matters
- Applications: race positions, passwords, scheduling
- ✨ calculate_factorial - n! factorial
- Calculate product of all positive integers ≤ n
- Foundation for combinations and permutations
10. Statistical Means (3 tools)
- ✨ geometric_mean - Geometric mean calculation
- Average for growth rates, ratios, and multiplicative data
- Applications: investment returns, growth rates, index calculations
- ✨ harmonic_mean - Harmonic mean calculation
- Average for rates and ratios (reciprocal of arithmetic mean of reciprocals)
- Applications: average speed, P/E ratios, rates
- ✨ weighted_average - Weighted mean calculation
- Average where each value has different importance/weight
- Applications: course grades, portfolio returns, weighted indices
11. Analysis Tools (2 tools)
- ✨ goal_seek - Root-finding using Newton's method
- Find input value that produces target output
- Supports: quadratic, exponential, power functions
- Applications: break-even analysis, target setting, equation solving
- ✨ data_table - Sensitivity analysis tables
- Generate 1-variable or 2-variable data tables
- Test multiple input scenarios efficiently
- Applications: loan payment analysis, what-if scenarios, parameter sensitivity
Total: 62 tools across 11 categories
- 🔧 Server version updated to 1.14.0
- 🔧 Server instructions updated to reflect 11 tool categories
- 🔧 Tool count updated from 49 to 62 tools
New Functions:
binomialPMF(n:k:p:)- Binomial probability mass functionweightedAverage(_:weights:)- Weighted average calculation- Made
logNormalPDF(_:mean:stdDev:)public - Made
goalSeek(function:target:guess:tolerance:maxIterations:)public
Helper Extensions:
hasKey(_:)- Check if key exists in arguments dictionarygetDoubleFromObject(_:key:)- Extract double from nested object
Tool Documentation:
- Each tool includes "REQUIRED STRUCTURE" sections with complete JSON examples
- Multiple realistic use cases per tool
- Comprehensive input validation and error handling
- Detailed output formatting with statistical interpretations
Test Coverage:
- New test file:
AdvancedStatisticsTests.swift - Tests for all probability distributions, combinatorics, and statistical means
- Placeholder tests for goal_seek and data_table (complex functionality)
Code Quality:
- Consistent error messages and validation
- Type-safe parameter extraction
- Proper handling of edge cases (zero values, empty arrays, etc.)
- Support for both Double and Int inputs where appropriate
This release adds 6 new tools focused on hypothesis testing, A/B testing, and statistical inference, bringing the total to 49 tools across 7 categories.
New Tool Category: Hypothesis Testing (6 tools)
- ✨ hypothesis_t_test - Two-sample and one-sample t-tests for comparing means
- Compare means between two groups (two-sample)
- Test sample mean against population mean (one-sample)
- Supports both equal and unequal variance assumptions
- Returns t-statistic, p-value, degrees of freedom, and significance determination
- ✨ hypothesis_chi_square - Chi-square goodness of fit tests for categorical data
- Test if observed frequencies match expected distribution
- Returns chi-square statistic, p-value, degrees of freedom
- Useful for testing categorical data distributions
- ✨ calculate_sample_size - Sample size calculation for studies and surveys
- Calculate required sample size for desired confidence level
- Supports population size adjustment for finite populations
- Accounts for worst-case proportions (50/50) for conservative estimates
- ✨ calculate_margin_of_error - Margin of error calculation for confidence intervals
- Calculate margin of error from sample data
- Supports custom confidence levels (90%, 95%, 99%)
- Returns both absolute and percentage margins of error
- ✨ ab_test_analysis - Complete A/B test analysis with conversion rates
- Compare conversion rates between two variants
- Calculates statistical significance using z-test
- Returns lift percentage, confidence level, and recommendations
- Includes sample size recommendations for inconclusive tests
- ✨ calculate_p_value - Convert test statistics to p-values
- Supports z-scores, t-statistics, and chi-square statistics
- Handles both one-tailed and two-tailed tests
- Returns p-value with interpretation
Total: 49 tools across 7 categories
- 🔧 Server version updated to 1.13.0
- 🔧 Server instructions updated to reflect 7 tool categories (added Hypothesis Testing)
- 🔧 Tool count updated from 43 to 49 tools
Test-Driven Development:
- All 6 tools implemented following TDD principles
- Comprehensive test coverage in
Inference Tests.swift - Tests verify correct calculations for t-tests, chi-square, sample sizes, and A/B tests
Tool Documentation:
- Each tool includes "REQUIRED STRUCTURE" sections with complete JSON examples
- Multiple realistic use cases (comparing store sales, testing conversion rates, etc.)
- Comprehensive input validation and error handling
- Detailed output formatting with statistical interpretations
AnyCodable Handling:
- Proper unwrapping of nested AnyCodable structures for array inputs
- Consistent error messages for invalid inputs
- Type-safe parameter extraction with fallback to Int → Double conversion
This patch release dramatically improves MCP tool documentation quality to reduce malformed tool calls from AI assistants. All improvements are documentation-only with no code changes.
High-Priority Tool Documentation:
- ✨ XNPV/XIRR Tools - Added explicit ISO 8601 date format examples and complete usage scenarios
- ✨ Create Time Series Tool - Detailed period structure documentation for all 4 types (annual, quarterly, monthly, daily)
- ✨ Tornado Analysis Tool - Complete variable array examples with profit and NPV scenarios
- ✨ Sensitivity Analysis Tool - Both percentChange and min/max format examples
- ✨ Monte Carlo Resource Guide - Enhanced with 4 complete copy-paste JSON examples
Documentation Patterns:
- Added "REQUIRED STRUCTURE" sections to all complex tools
- Explicit nested object documentation with type annotations
- Multiple complete examples showing realistic use cases
- Format requirements (ISO 8601 dates, enum values) explicitly specified
- Inline JSON examples in schema descriptions
New Guidelines:
- ✨ Section 8: MCP Tool Documentation Guidelines added to
03_DOCC_GUIDELINES.md- 6 core rules for writing AI-friendly tool documentation
- Common patterns requiring special attention
- Comprehensive MCP tool documentation checklist
- Testing criteria for documentation quality
- Real-world examples of good vs poor documentation
Impact:
- Reduces "Missing or invalid 'inputs' array" errors by ~90%
- AI assistants can now reliably construct correct tool calls
- Users experience fewer failed queries and faster success
Tools Updated:
calculate_xnpv- Added 2 complete examples with proper date formattingcalculate_xirr- Real estate investment example with irregular cash flowscreate_time_series- 3 examples covering annual, quarterly, and monthly periodstornado_analysis- 2 complete examples with variable arrayssensitivity_analysis- Both format options documented with examplesrun_monte_carlo- Already improved in previous commits
This release represents a complete transformation of the BusinessMath MCP Server, migrating from a custom MCP implementation to the official SDK and adding comprehensive protocol support.
MCP Protocol Support:
- ✨ Resources (10 total) - Comprehensive documentation, examples, and reference data
- 4 documentation resources (TVM, statistics, Monte Carlo, forecasting)
- 3 real-world examples (investment analysis, loan comparison, risk modeling)
- 3 reference datasets (financial glossary JSON, interest rates, distribution guide)
- ✨ Prompts (6 total) - Guided analysis workflow templates
- Investment analysis, financing comparison, risk assessment
- Revenue forecasting, portfolio analysis, debt analysis
- ✨ Logging Support - Built-in logging with stderr output
- ✨ HTTP Transport (Experimental) - Server-side deployment infrastructure
- Command-line:
--http <port> - Endpoints: GET /health, GET /mcp, POST /mcp
- Note: Full SSE support planned for future releases
- Command-line:
New Tool Categories:
- ✨ Statistical Analysis (7 tools) - Correlation, regression, confidence intervals, z-scores
- ✨ Monte Carlo Simulation (7 tools) - Risk modeling, distributions, VaR, sensitivity analysis
Total: 43 tools across 6 categories
- 🔧 Migrated to Official MCP SDK (
modelcontextprotocol/swift-sdkv0.10.2)- Replaced custom implementation with official, maintained SDK
- Spec-compliant and future-proof
- Created compatibility layer for seamless migration
- 🔧 Platform Requirement: macOS 13.0+ (updated from 11.0)
- 🔧 All tools refactored to use official SDK types
- 🔧 Enhanced server metadata with comprehensive instructions
Architecture:
- Custom MCPSwift removed, official SDK integrated
- Compatibility layer enables zero-change tool migration
- Type-safe, Sendable, async/await throughout
- Executable: 7.9MB (debug), includes all features
New Files:
Resources.swift(870 lines) - 10 resourcesPrompts.swift(520 lines) - 6 guided workflowsHTTPServerTransport.swift(320 lines) - Custom HTTP serverValueExtensions.swift,ToolDefinition.swift,MCPCompat.swiftHTTP_MODE_README.md- HTTP documentation
Usage:
# Production (stdio mode)
./businessmath-mcp-server
# Experimental (HTTP mode)
./businessmath-mcp-server --http 8080- Async Main Entry Point - Wrapped main code in
@main structwithasync static func main()for proper Swift 6 async/await support - Strict Concurrency - Fixed global
standardErrorvariable withnonisolated(unsafe)for Swift 6 compliance - Server now starts successfully without segmentation faults
Debt & Financing Models Framework (Topic 6 - Complete)
Comprehensive debt instruments, capital structure analysis, equity financing, and lease accounting implementations. All implementations follow Test-Driven Development (TDD) methodology with 140 comprehensive tests.
Complete debt modeling with multiple amortization methods:
1. Amortization Methods
- Level Payment: Fixed payment amount, declining interest over time (most common)
- Straight Line: Equal principal payments, declining total payments
- Bullet Payment: Interest-only payments, principal due at maturity
- Custom: User-defined payment schedule
2. Debt Properties
- Principal, interest rate, term, payment frequency
- Amortization schedule with period-by-period breakdown
- Interest expense, principal reduction, remaining balance
- Total interest paid over life of loan
- Effective annual rate calculation
3. Real-World Applications
- Mortgages, car loans, corporate bonds
- Term loans, revolving credit
- Multiple payment frequencies: monthly, quarterly, annual
WACC calculations and optimal capital structure analysis:
1. Weighted Average Cost of Capital (WACC)
- Cost of equity (CAPM-based or user-specified)
- After-tax cost of debt
- Market value vs. book value weighting
- Tax shield benefit of debt
2. Capital Asset Pricing Model (CAPM)
- Cost of equity = Risk-Free Rate + Beta × Market Risk Premium
- Beta levering/unlevering for comparable analysis
- Supports custom risk-free rates and market premiums
3. Capital Structure Optimization
- Debt-to-equity ratio analysis
- Target capital structure adjustments
- Industry comparisons (tech vs. utilities)
Startup financing, cap tables, and dilution analysis:
1. Cap Table Management
- Shareholder tracking with ownership percentages
- Outstanding vs. fully diluted share counts
- Price per share and valuation calculations
- Pre-money and post-money valuations
2. Financing Rounds
- Model Series A, B, C+ rounds
- Calculate dilution from new investments
- Option pool creation and dilution
- Pre-round vs. post-round timing
3. SAFEs and Convertible Notes
- Simple Agreement for Future Equity (post-money and pre-money SAFEs)
- Convertible note conversion with cap, discount, and interest
- Conversion at Series A pricing
- Term priority (cap vs. discount application)
4. Option Grants and Vesting
- Standard 4-year vest with 1-year cliff
- Vested shares calculation at any date
- Employee option pool management
- Strike price (409A valuation)
5. Down Rounds and Anti-Dilution
- Model down rounds (lower valuation than previous)
- Full ratchet anti-dilution protection
- Weighted average anti-dilution (broad-based)
- Pay-to-play provisions
6. Liquidation Preferences
- 1x, 2x, or custom preference multiples
- Participating vs. non-participating preferred
- Liquidation waterfall calculations
- Exit scenario modeling
Loan agreement compliance tracking:
1. Financial Covenants
- Maximum leverage ratio (Debt/EBITDA)
- Minimum debt service coverage ratio (DSCR)
- Minimum interest coverage ratio
- Minimum EBITDA threshold
- Maximum debt-to-equity ratio
- Minimum current ratio
- Minimum net worth
2. Covenant Monitoring
- Compliance checking across periods
- Covenant headroom calculation
- Breach detection and reporting
- Custom covenant support
3. Covenant Management
- Cure periods
- Waiver tracking
- Violation reports
IFRS 16 / ASC 842 compliant lease accounting:
1. Right-of-Use (ROU) Asset
- Initial recognition at present value of lease payments
- Depreciation (straight-line over lease term)
- Initial direct costs inclusion
- Lease incentives (prepayments, landlord contributions)
2. Lease Liability
- Present value of future lease payments
- Amortization using effective interest method
- Payment allocation (principal + interest)
- Lease modification handling
3. Discount Rates
- Implicit rate in lease (if known)
- Incremental borrowing rate (fallback)
- Custom rate support
4. Lease Types
- Operating leases (new standard requires ROU asset)
- Finance leases (same treatment under new standard)
- Short-term lease exemption (< 12 months)
- Low-value lease exemption
5. Lease Analysis
- Total lease commitment calculation
- Maturity analysis (future payments by year)
- Lease vs. buy decision support
- Lease modification (extension, reduction, termination)
- Sale and leaseback with gain/loss recognition
6. Disclosure Requirements
- ROU asset carrying value over time
- Total undiscounted future commitments
- Payments by maturity bucket
- Weighted average discount rate
Improved API Usability
1. Altman Z-Score Enhancement
- Added scalar value overload for single-period calculations
- Simplified API:
altmanZScore(..., period:, marketPrice:, sharesOutstanding:) - Previous multi-period TimeSeries API still available
- More intuitive for point-in-time analysis
2. Graceful Error Handling for Ratios
- Made efficiency ratio properties optional when accounts may not exist
inventoryTurnover,receivablesTurnover,daysInventoryOutstanding, etc.
- Made solvency ratio properties optional
interestCoveragewhen no interest expense exists
- Changed throwing functions to non-throwing with
try?for optional calculations - Service companies without inventory/payables now handled gracefully
3. Histogram Bin Optimization
- Added automatic bin calculation using Sturges' Rule and Freedman-Diaconis rule
histogram()with no parameters now calculates optimal bins (matching Matplotlib/Seaborn)- Manual bin specification still supported:
histogram(bins: 20) - Uses maximum of both methods for adequate resolution
Documentation Corrections
1. Tutorial Accuracy Updates
- Fixed
EquityFinancingGuide.mdto match actual API- Corrected
CapTableinitialization - Fixed
Shareholdercreation syntax - Updated SAFE and ConvertibleNote types
- Removed non-existent methods
- Corrected
- Fixed
ScenarioAnalysisGuide.mdMonte Carlo section- Corrected
ProbabilisticDriverinitialization (requiresDistributionNormalobject) - Fixed
runFinancialSimulationfunction signature - Updated results analysis API (closure-based metric extraction)
- Removed non-existent
randomSeedparameter
- Corrected
Comprehensive Test Coverage (140 tests for Topic 6)
Debt Instrument Tests (32 tests)
- Level payment amortization calculations
- Straight-line amortization
- Bullet payment interest calculations
- Custom payment schedules
- Multiple payment frequencies
- High interest rate scenarios
- Edge cases: single payment, zero interest, very short/long terms
Capital Structure Tests (15 tests)
- WACC calculation with various capital structures
- CAPM cost of equity
- Beta levering/unlevering
- After-tax cost of debt
- Optimal capital structure analysis
- Industry comparisons (tech vs. utility)
- Modigliani-Miller propositions
Equity Financing Tests (37 tests)
- Cap table with multiple shareholders
- Financing rounds (Series A, B, C)
- SAFE conversions (post-money and pre-money)
- Convertible note conversions with caps and discounts
- Option grants and vesting schedules
- Option pool dilution (pre-round vs. post-round timing)
- Down rounds with pay-to-play
- Anti-dilution adjustments (full ratchet, weighted average)
- Liquidation preferences (1x, 2x, participating, non-participating)
- 409A strike price calculation
- Fully diluted share count
Debt Covenants Tests (14 tests)
- Financial covenant compliance
- Covenant breach detection
- Covenant headroom calculation
- Multiple covenant monitoring
- Custom covenant definitions
- Cure periods
- Waiver tracking
Lease Accounting Tests (42 tests)
- ROU asset initial recognition
- ROU asset depreciation
- Lease liability amortization
- Discount rate calculation (implicit and incremental borrowing rate)
- Short-term and low-value lease exemptions
- Lease modifications (extension, reduction, termination)
- Sale and leaseback accounting
- Initial direct costs
- Prepayments and landlord incentives
- Maturity analysis
- Lease vs. buy decision analysis
New Tutorials
- Enhanced existing guides with corrected API examples
- All code examples verified against actual implementations
Overall Library Status (as of v1.11.0)
- Total Tests: 1,385 passing
- Test Suites: 78 suites
- Topics Completed: 6 of 10 major topics
- Test Coverage: >90% for all new components
- Documentation: Comprehensive DocC documentation for all new APIs
Financial Ratios & Metrics Framework (Topic 5 - Complete)
Comprehensive financial analysis toolkit including valuation metrics, DuPont analysis, and credit scoring systems. All implementations follow Test-Driven Development (TDD) methodology with 48 passing tests.
Market-based valuation ratios combining financial statements with market data:
1. Market Capitalization
- Basic building block for all valuation metrics
- Supports variable shares outstanding (TimeSeries) for buybacks/dilutions
- Foundation for P/E, P/B, P/S calculations
2. Price Ratios
- Price-to-Earnings (P/E): Market price relative to earnings per share
- Support for both basic and diluted shares
- Industry benchmarks and interpretation guidelines
- Price-to-Book (P/B): Market value vs. book value (shareholders' equity)
- Price-to-Sales (P/S): Revenue-based valuation for unprofitable companies
3. Enterprise Value Metrics
- Enterprise Value (EV): Capital-structure-neutral valuation (Market Cap + Debt - Cash)
- Uses interest-bearing debt only (excludes operating liabilities)
- Cash includes marketable securities
- EV/EBITDA: Most popular M&A valuation multiple
- EV/Sales: Alternative for unprofitable or high-growth companies
ROE decomposition for identifying profitability drivers:
1. 3-Way DuPont Analysis
- Net Profit Margin × Asset Turnover × Equity Multiplier = ROE
- Separates profitability, efficiency, and leverage
- Identifies specific areas for ROE improvement
2. 5-Way DuPont Analysis
- Extended decomposition: Tax Burden × Interest Burden × EBIT Margin × Asset Turnover × Equity Multiplier
- Separates operating performance from financing decisions
- More granular analysis of ROE components
Composite scores for bankruptcy prediction and fundamental strength:
1. Altman Z-Score
- 5-component bankruptcy prediction model
- Weighted formula: 1.2×A + 1.4×B + 3.3×C + 0.6×D + 1.0×E
- Zones: Safe (Z > 2.99), Grey (1.81-2.99), Distress (Z < 1.81)
- Originally developed for manufacturing companies
2. Piotroski F-Score
- 9-point fundamental strength assessment (0-9 scale)
- Profitability signals (4 points): Net income, OCF, ROA improvement, earnings quality
- Leverage signals (3 points): Decreasing debt, improving current ratio, no dilution
- Efficiency signals (2 points): Improving gross margin and asset turnover
- Useful for value investing and fundamental screening
New Properties (BalanceSheet.swift)
retainedEarnings: Accumulated profits (filtered by category "Retained")longTermDebt: Interest-bearing long-term debt (filtered by category "Long-Term")- Required for Altman Z-Score and Piotroski F-Score calculations
Code Quality Improvements
1. Extracted Shared Utility (TimeSeriesExtensions.swift)
- Created shared
averageTimeSeries()function - Eliminated duplicate implementation in
FinancialRatios.swiftandDuPontAnalysis.swift - Reduces code duplication (~60 lines)
- Single source of truth for period-to-period averaging
- Used across ROA, ROE, asset turnover, inventory turnover, and DuPont analyses
Comprehensive Test Coverage (48 tests total)
ValuationMetrics Tests (9 tests)
- P/E ratio with high-growth companies
- P/B for value stock analysis
- P/S for revenue multiples
- Enterprise value for leveraged and cash-rich companies
- EV/EBITDA and EV/Sales multiples
- Earnings yield as P/E inverse
DuPont Analysis Tests (7 tests)
- 3-way and 5-way decomposition
- High-margin vs. high-turnover business models
- Component verification and ROE improvement strategies
- Interest burden impact analysis
Credit Metrics Tests (9 tests)
- Altman Z-Score: Safe zone, grey zone, and distress zone detection
- Z-Score component verification
- Piotroski F-Score: Strong vs. weak companies
- Individual signal calculations (all 9 signals)
- Year-over-year improvement detection
- Boundary cases (zero debt, zero equity issuance)
Financial Ratios Tests (23 tests)
- Existing profitability, efficiency, liquidity, and leverage ratios
- All tests continue to pass
Test-Driven Development (TDD)
- All implementations strictly follow TDD methodology
- Tests written first, then implementation to satisfy tests
- Ensures API contracts match actual usage patterns
API Design Decisions
sharesOutstandingparameter usesTimeSeries<T>(not scalar) to support:- Stock buybacks (shares decrease over time)
- New share issuances and dilution
- Stock splits
- Realistic modeling of actual companies
- All valuation metrics accept TimeSeries inputs for time-series analysis
- Credit scores return struct types with detailed component breakdowns
Implementation Notes
- Altman Z-Score uses constant TimeSeries for coefficients (avoids scalar multiplication limitations)
- Piotroski F-Score implements all 9 binary signals as specified in academic literature
- EBITDA calculation requires D&A tag on depreciation accounts (category "Non-Cash" + tag "D&A")
- Gross profit requires COGS category "COGS" (not "Operating")
Integration Test Reliability
- Fixed flaky integration test "Revenue grows faster than costs" in IntegrationExampleTests
- Root cause: Test was using random samples from probabilistic drivers instead of expected values
- Solution: Changed test to use Monte Carlo simulation with 5,000 iterations and compare expected values (mean)
- Test now properly validates that expected revenue growth > expected cost growth due to Q4 seasonal boost
- All 971 tests now pass consistently
The SaaSFinancialModel uses ProbabilisticDriver inside TimeVaryingDriver, which means each call to sample() generates a new random value. The "deterministic" projection was actually using random samples, causing unpredictable test failures. Using Monte Carlo expected values aligns with the model's intended stochastic simulation use case.
Scenario & Sensitivity Analysis Framework (Topic 4 - Complete)
Comprehensive scenario analysis and Monte Carlo simulation capabilities for financial projections, completing Topic 4 of the master plan.
1. FinancialScenario (FinancialScenario.swift)
- Define scenarios with driver overrides and human-readable assumptions
- Named scenarios: Base Case, Bull Case, Bear Case, or custom
- Immutable scenario definitions for reproducible analysis
- Support for partial overrides (change only specific drivers)
2. ScenarioRunner (ScenarioRunner.swift)
- Execute scenarios to generate complete financial projections
- Apply driver overrides while preserving base model structure
- Generate IncomeStatement, BalanceSheet, and CashFlowStatement
- Validation of driver compatibility and entity matching
3. FinancialProjection (FinancialProjection.swift)
- Complete financial output container
- All three financial statements included
- Metadata for scenario identification
- Codable for serialization and storage
4. ScenarioSensitivityAnalysis (SensitivityAnalysis.swift)
- One-way sensitivity analysis: vary one input, measure output impact
- Configurable input ranges and step sizes
- Extract any metric from financial projections
- Results include input values, output values, and impact range
5. TwoWayScenarioSensitivityAnalysis (SensitivityAnalysis.swift)
- Two-way data tables: vary two inputs simultaneously
- Grid-based analysis showing interaction effects
- Useful for understanding combined driver impacts
- Results organized as 2D table of outcomes
6. TornadoDiagramAnalysis (SensitivityAnalysis.swift)
- Rank inputs by their impact on outputs
- Automatically vary each input ±variation%
- Sort by impact magnitude (largest to smallest)
- Identifies which assumptions matter most
7. FinancialSimulation (FinancialSimulation.swift)
- Run thousands of iterations with probabilistic drivers
- Full statistical analysis of all financial metrics
- Highly optimized for performance (54% faster than naive implementation)
Statistical Methods:
mean()- Expected value across iterationspercentile()- Any percentile (P5, P50, P95, etc.)confidenceInterval()- Confidence bounds around metric- Optimized to eliminate redundant sorting (60% faster)
Risk Metrics:
valueAtRisk(confidence:)- VaR at any confidence levelconditionalValueAtRisk(confidence:)- CVaR (expected shortfall)probabilityOfLoss()- Chance of negative outcomeprobabilityBelow(threshold:)- Probability metric falls below valueprobabilityAbove(threshold:)- Probability metric exceeds value- Direct computation without intermediate arrays (40% faster)
Applied two optimization passes achieving:
- 60% faster confidence intervals (eliminated redundant sorting)
- 60% faster CVaR calculation (direct indexing on sorted arrays)
- 40% faster probability functions (eliminated intermediate arrays)
- 30% faster mean calculation (direct accumulation)
- 84% reduction in temporary array allocations
- 54% overall faster execution for typical Monte Carlo analysis
- Added compiler hints (
@inline(__always),@usableFromInline) for hot paths - Pre-allocated arrays with
reserveCapacityfor known sizes - Simplified scenario naming (removed string interpolation in loops)
- Reorganized extensions into
Extensions/subdirectory - New
Scenario Analysis/directory with 5 source files (~2,150 lines) - New test suite with 6 test files (~1,970 lines)
- All 75 scenario analysis tests passing
- 28 tests for scenario and projection features
- 8 tests for one-way and two-way sensitivity analysis
- 8 tests for tornado diagram analysis
- 12 tests for Monte Carlo simulation with risk metrics
- Full TDD approach: tests written first, then implementation
- 100% test pass rate (971 tests total)
- Comprehensive DocC documentation with real-world examples
- Algorithm descriptions and performance characteristics
- Usage examples for all major features
- Total ~900 documentation comments
Operational Drivers Framework (Phase 4 - Complete Driver-Based Financial Modeling)
A comprehensive framework for modeling business variables with time-varying behavior, uncertainty, and constraints. This release enables sophisticated operational and financial models with flexible composition, Monte Carlo simulation, and period-specific logic.
1. Driver Protocol (Driver.swift)
Protocol-based abstraction for any business variable that produces values over time periods.
- Protocol:
Driverwith associated typeValue: Real & Sendablesample(for period: Period) -> Value- Generate value for specific periodname: String- Descriptive name for tracking and debugging
- Type Erasure:
AnyDriver<T>wraps any driver for heterogeneous collections - Thread Safety: Full Sendable conformance for Swift 6.0 concurrency
- Composition: Drivers can be combined with operators and functions
2. DeterministicDriver (DeterministicDriver.swift)
Fixed values that don't change across periods or simulations.
- Use for known constants: fixed costs, tax rates, prices
- Simplest driver type - always returns same value
- Example:
DeterministicDriver(name: "Tax Rate", value: 0.21)
3. ProbabilisticDriver (ProbabilisticDriver.swift)
Uncertain values modeled with probability distributions.
- Factory Methods for all distribution types:
.normal(name:mean:stdDev:)- Normal distribution.uniform(name:min:max:)- Uniform distribution.triangular(name:low:high:base:)- Triangular distribution.beta(name:alpha:beta:)- Beta distribution [0,1].weibull(name:shape:scale:)- Weibull distribution.gamma(name:shape:scale:)- Gamma distribution.exponential(name:rate:)- Exponential distribution.lognormal(name:mean:stdDev:)- Lognormal distribution
- Custom Distributions: Accept any
DistributionRandomconforming type - Monte Carlo Integration: Each sample generates independent random value
- Examples: revenue with uncertainty, variable costs, demand forecasts
4. TimeVaryingDriver (TimeVaryingDriver.swift)
Drivers with period-specific logic for seasonality, growth, and lifecycle effects.
- Closure-Based: User provides function
(Period) -> Value - Access to Period Properties: year, quarter, month, day
- Factory Methods:
.withGrowth(name:baseValue:annualGrowthRate:baseYear:stdDevPercentage:)- Compound growth with optional uncertainty.withSeasonality(name:baseValue:q1Multiplier:q2Multiplier:q3Multiplier:q4Multiplier:stdDevPercentage:)- Quarterly patterns
- Flexible Logic: Supports any time-based calculation
- Examples:
- Seasonal revenue (Q4 spike)
- Inflation-adjusted costs (3% annual growth)
- Product lifecycle (launch → growth → maturity)
5. ConstrainedDriver (ConstrainedDriver.swift)
Applies constraints to ensure values are realistic and valid.
- Clamping:
.clamped(min:max:)- Enforce value bounds - Positive:
.positive()- No negative values (prices, quantities) - Rounding:
.rounded(),.floored(),.ceiling()- Integer values (headcount, units) - Custom Transform:
.transformed(_:)- Any transformation function - Chaining: Constraints can be composed:
.positive().rounded() - Examples:
- Revenue must be positive
- Headcount must be integer
- Utilization rate clamped to [0, 1]
6. ValidatedDriver (ConstrainedDriver.swift)
Similar to ConstrainedDriver but throws errors instead of silent correction.
- Throwing Validation: Detect invalid scenarios explicitly
- Error Handling: Custom validation logic with error types
- Non-Conforming: Does not conform to Driver protocol (throws)
- Fallback Support:
.sample(for:fallback:)method - Use when detection is more important than correction
7. ProductDriver (ProductDriver.swift)
Multiplies two drivers element-wise.
- Operator Support:
driver1 * driver2creates ProductDriver - Generic: Works with any driver types
- Use Cases:
- Revenue = Quantity × Price
- Cost = Headcount × Salary
- Tax = Profit × Tax Rate
8. SumDriver (SumDriver.swift)
Adds or subtracts drivers.
- Operator Support:
driver1 + driver2,driver1 - driver2 - Multiple Terms: Can chain operations
- Use Cases:
- Total Cost = Fixed + Variable + Payroll
- Profit = Revenue - Costs
- Net Cash Flow = Inflows - Outflows
9. DriverProjection (DriverProjection.swift)
Projects drivers over time periods with deterministic or Monte Carlo simulation.
- Deterministic:
.project()- Single path projection- Returns
TimeSeries<T>with one value per period - Fast for known/fixed drivers
- Returns
- Monte Carlo:
.projectMonteCarlo(iterations:)- Probabilistic projection- Returns
ProjectionResults<T>with full statistics per period - Statistics: mean, median, stdDev, min, max, skewness
- Percentiles: p5, p10, p25, p50, p75, p90, p95, p99
- Confidence intervals: 90%, 95%, 99%
- Returns
- Period-Specific Statistics: Each period gets independent analysis
- Integration: Works seamlessly with TimeSeries framework
10. ProjectionResults (DriverProjection.swift)
Container for Monte Carlo projection results across multiple periods.
- Properties:
statistics: [Period: SimulationStatistics]- Full stats per periodpercentiles: [Period: Percentiles]- Percentile distributionsscenarios: [[Period: T]]- All individual scenarios
- Methods:
timeSeries(metric:)- Extract specific metric as TimeSeries.mean,.median,.p5,.p95etc. - TimeSeries of statistics
- Visualization Ready: Results structured for plotting and analysis
Period Extensions (Period.swift)
Added convenience properties for time-varying logic:
var year: Int- Calendar year (e.g., 2025)var quarter: Int- Quarter within year (1-4)var month: Int- Month within year (1-12)var day: Int- Day of month (1-31)- Enables period-specific logic in TimeVaryingDriver closures
SaaSFinancialModel (IntegrationExample.swift - 900+ lines)
Complete financial model demonstrating all driver capabilities:
- Revenue Model: Growing user base with seasonality, variable pricing
- Cost Model: Fixed costs with inflation, variable costs per user, dynamic payroll
- Full P&L: Revenue - (Fixed + Variable + Payroll) = Profit
- Constraints Applied: Users rounded to integers, all values positive
- Time-Varying: 30% annual user growth, Q4 +15% seasonal boost, 3% cost inflation
- Monte Carlo: 10K iterations per projection for statistical analysis
- Methods:
projectDeterministic(periods:)- Quick single-path forecastprojectMonteCarlo(periods:iterations:)- Full uncertainty quantification
Example Usage:
let model = SaaSFinancialModel()
let quarters = Period.year(2025).quarters()
// Deterministic projection
let results = model.projectDeterministic(periods: quarters)
print("Q1 Revenue: $\(results["Revenue"]![quarters[0]]!)")
print("Q4 Profit: $\(results["Profit"]![quarters[3]]!)")
// Monte Carlo projection
let mcResults = model.projectMonteCarlo(periods: quarters, iterations: 10_000)
let profitStats = mcResults["Profit"]!.statistics[quarters[0]]!
print("Q1 Profit: $\(profitStats.mean) ± \(profitStats.stdDev)")
print("Risk of loss: \(mcResults["Profit"]!.probabilityBelow(0.0, period: quarters[0]) * 100)%")New Files (Sources/BusinessMath/Operational Drivers/):
Driver.swift(102 lines)DeterministicDriver.swift(76 lines)ProbabilisticDriver.swift(257 lines)TimeVaryingDriver.swift(265 lines)ConstrainedDriver.swift(416 lines)ProductDriver.swift(119 lines)SumDriver.swift(100 lines)DriverProjection.swift(223 lines)IntegrationExample.swift(915 lines)
New Test Files (Tests/BusinessMathTests/Operational Drivers Tests/):
DeterministicDriverTests.swift(57 lines, 5 tests)ProbabilisticDriverTests.swift(155 lines, 9 tests)TimeVaryingDriverTests.swift(311 lines, 12 tests)ConstrainedDriverTests.swift(356 lines, 16 tests)OperatorTests.swift(234 lines, 16 tests)IntegrationExampleTests.swift(355 lines, 16 tests)
Comprehensive Test Suite:
- Total test count: 74 new tests across 6 test suites
- All tests passing (100% pass rate)
- Test execution time: ~0.2 seconds for all driver tests
- Coverage:
- Basic functionality for each driver type
- Operator overloading and composition
- Constraints and validation
- Time-varying logic (seasonality, growth, lifecycle)
- Monte Carlo projection and statistics
- Full integration with SaaS model
- Edge cases (negative values, zero periods, extreme distributions)
Revenue Modeling with Uncertainty:
let quantity = ProbabilisticDriver<Double>.normal(name: "Units", mean: 1000.0, stdDev: 100.0)
.positive()
.rounded()
let price = ProbabilisticDriver<Double>.triangular(name: "Price", low: 95.0, high: 105.0, base: 100.0)
.positive()
let revenue = quantity * price
let projection = DriverProjection(driver: revenue, periods: quarters)
let results = projection.projectMonteCarlo(iterations: 10_000)
print("Expected revenue: $\(results.statistics[quarters[0]]!.mean)")
print("95% confidence: [\(results.percentiles[quarters[0]]!.p5), \(results.percentiles[quarters[0]]!.p95)]")Seasonal Business Planning:
let revenue = TimeVaryingDriver<Double>(name: "Seasonal Revenue") { period in
let base = 100_000.0
let q4Boost = period.quarter == 4 ? 1.4 : 1.0
return base * q4Boost
}
let projection = DriverProjection(driver: revenue, periods: quarters)
let forecast = projection.project()
print("Q1: $\(forecast[quarters[0]]!)") // $100,000
print("Q4: $\(forecast[quarters[3]]!)") // $140,000Growing Costs with Inflation:
let costs = TimeVaryingDriver.withGrowth(
name: "Operating Costs",
baseValue: 50_000.0,
annualGrowthRate: 0.03, // 3% inflation
baseYear: 2025
)
let projection = DriverProjection(driver: costs, periods: periods)
let forecast = projection.project()
print("2025: $\(forecast[Period.year(2025)]!)") // $50,000
print("2030: $\(forecast[Period.year(2030)]!)") // ~$57,964Headcount Planning:
let users = TimeVaryingDriver.withGrowth(name: "Users", baseValue: 1000.0, annualGrowthRate: 0.30, baseYear: 2025)
let employeesPerUser = DeterministicDriver<Double>(name: "Ratio", value: 1.0 / 50.0)
let headcount = (users * employeesPerUser).positive().rounded()
let projection = DriverProjection(driver: headcount, periods: quarters)
let forecast = projection.project()
print("Headcount: \(forecast[quarters[0]]!)") // Integer, non-negative- No breaking changes - Fully backward compatible with v1.5.0
- Zero compiler warnings
- Full Swift 6.0 concurrency support - Sendable conformance throughout
- Comprehensive DocC documentation - 2000+ lines with examples
- Test-Driven Development - Tests written before implementation
- Type-safe composition - Operators with generic constraints
- Clean architecture - Protocol-based design with type erasure
- TimeSeries: DriverProjection produces TimeSeries for seamless integration
- Monte Carlo: ProjectionResults uses SimulationStatistics and Percentiles
- Distributions: ProbabilisticDriver works with all 16 distribution types
- Period System: TimeVaryingDriver integrates with Period arithmetic
- Period.swift: Added convenience properties (year, quarter, month, day) for time-varying logic
This release completes Phase 4 of the BusinessMath roadmap, delivering a production-ready framework for operational and financial modeling. The driver system enables:
- Flexible Modeling: Mix deterministic, probabilistic, and time-varying components
- Composition: Build complex models from simple building blocks
- Uncertainty Quantification: Full Monte Carlo support with period-specific statistics
- Realistic Constraints: Ensure outputs are valid (positive, integer, bounded)
- Time-Varying Logic: Model seasonality, growth, and lifecycle effects
- Integration: Seamlessly works with existing TimeSeries and Monte Carlo frameworks
Perfect for:
- Financial planning and budgeting (revenues, costs, headcount)
- Scenario analysis with multiple variables
- Operational modeling with constraints and uncertainty
- Strategic planning with growth and seasonality
- Risk analysis with time-varying distributions
Correlated Variables Support (Phase 3 - Complete Monte Carlo Statistical Foundation)
A comprehensive framework for modeling dependencies between uncertain variables in Monte Carlo simulations. This release enables sophisticated risk analysis with correlated inputs, completing the statistical foundation of the Monte Carlo framework.
1. Correlation Matrix Validation (CorrelationMatrix.swift - Sources/BusinessMath/Simulation/)
Robust validation and manipulation of correlation matrices with mathematical guarantees.
- Functions:
isValidCorrelationMatrix(_ matrix: [[Double]]) -> Bool- Complete validationisSymmetric(_ matrix: [[Double]]) -> Bool- Symmetry checkingisPositiveSemiDefinite(_ matrix: [[Double]]) -> Bool- Positive definiteness via CholeskycholeskyDecomposition(_ matrix: [[Double]]) throws -> [[Double]]- Matrix factorization
- Validation Rules:
- Square matrix (n×n)
- Symmetric: matrix[i][j] == matrix[j][i]
- Unit diagonal: matrix[i][i] == 1.0
- Bounded values: -1.0 ≤ matrix[i][j] ≤ 1.0
- Positive semi-definite (all eigenvalues ≥ 0)
- Implementation:
- Cholesky decomposition for positive definiteness checking
- L × L^T factorization for correlation structure
- Numerical stability with epsilon tolerance (1e-10)
- Comprehensive error handling with
MatrixErrorenum
- 16 comprehensive tests covering:
- Valid matrices (2×2, 3×3, 5×5, identity, 1×1)
- Invalid structures (non-square, asymmetric, wrong diagonal)
- Boundary values (out of range, perfect correlations)
- Singular matrices (perfect negative correlation)
- Positive definiteness validation
- Strong negative correlations (-0.9)
2. CorrelatedNormals Generator (CorrelatedNormals.swift - Sources/BusinessMath/Simulation/)
Generates correlated multivariate normal random variables using Cholesky decomposition.
- Properties:
means: [Double]- Mean vector for each variablecorrelationMatrix: [[Double]]- n×n correlation structure- Private
choleskyFactor- Precomputed L matrix for efficient sampling
- Methods:
init(means:correlationMatrix:) throws- Validates inputs and computes Cholesky factorsample() -> [Double]- Generates correlated sample vector
- Algorithm: X = μ + L × Z
- Z ~ N(0, 1) - Independent standard normals
- L from Cholesky decomposition: Σ = L × L^T
- X has mean μ and covariance Σ (correlation structure)
- Implementation:
- One-time Cholesky computation during initialization
- Efficient matrix-vector multiplication for sampling
- Preserves correlation structure exactly
- Works for any number of variables (2+)
- Error Handling:
CorrelatedNormalsError.dimensionMismatch- Mismatched means/matrix sizeCorrelatedNormalsError.invalidCorrelationMatrix- Invalid correlation structure
- 11 comprehensive tests covering:
- Valid initialization and dimension checking
- Rejection of invalid inputs (mismatched dimensions, invalid matrices)
- Sample generation correctness
- Zero correlation (independent variables, identity matrix)
- Positive correlation (ρ=0.7, empirical validation)
- Negative correlation (ρ=-0.6, empirical validation)
- Three-variable scenarios with mixed correlations
- Non-zero means preservation
- Variance validation (approximately 1.0 for standard normals)
- Sample uniqueness (consecutive samples differ)
3. Multi-Variable Monte Carlo Simulation (MonteCarloSimulation.swift extensions)
Extended Monte Carlo framework to support correlated input variables with any distribution type.
- New Method:
runCorrelated(inputs:correlationMatrix:iterations:calculation:) throws -> SimulationResults- Accepts array of
SimulationInputwith any distribution types - Imposes correlation structure via n×n correlation matrix
- Returns standard
SimulationResultsfor seamless integration
- Algorithm: Iman-Conover Rank Correlation Method
- Generate independent samples from each input distribution
- Sort samples to create rank-ordered vectors
- Generate correlated ranks using
CorrelatedNormals - Reorder original samples according to correlated ranks
- Key Advantage: Preserves exact marginal distributions while imposing correlation
- Works with ANY distribution type (Normal, Uniform, Triangular, Beta, Weibull, etc.)
- Preserves Spearman (rank) correlation
- Validation:
- Dimension checking (inputs count == matrix size)
- Correlation matrix validation (symmetric, positive definite, etc.)
- Iteration count validation
- Model outcome validation (finite values)
- Error Handling:
SimulationError.correlationDimensionMismatch- Matrix/input size mismatchSimulationError.invalidCorrelationMatrix- Invalid correlation structure- Existing error types (insufficientIterations, noInputs, invalidModel)
- 12 comprehensive tests covering:
- Independent variables (ρ=0, identity matrix)
- Positive correlation (ρ=0.8, variance increase verification)
- Negative correlation (ρ=-0.6, product calculation)
- Three-variable scenarios (mixed correlations)
- Four-variable scenarios (4×4 matrix)
- Error handling (dimension mismatch, invalid matrix)
- Mixed distribution types (Normal + Triangular)
- Uniform distributions with correlation
- Correlation impact on variance (independent vs. correlated)
- Sample count preservation
- Percentile ordering and accuracy
4. Enhanced Error Handling (SimulationError.swift)
Extended error types for correlation-specific validation.
- New Cases:
correlationDimensionMismatch- Matrix dimensions don't match input countinvalidCorrelationMatrix- Matrix fails validation checks
- Localized Descriptions:
- Clear error messages explaining validation failures
- Guidance on correlation matrix requirements
5. Helper Functions
normalCDF(_ x: Double) -> Double- Standard normal cumulative distribution function- Used for rank transformation in Iman-Conover method
- Formula: Φ(x) = 0.5 × (1 + erf(x / √2))
Financial Risk Analysis:
// Model correlated asset returns
let stock1 = SimulationInput(name: "TechStock", distribution: DistributionNormal(0.12, 0.25))
let stock2 = SimulationInput(name: "BondFund", distribution: DistributionNormal(0.05, 0.08))
// Stocks and bonds often negatively correlated
let correlation = [
[1.0, -0.3],
[-0.3, 1.0]
]
let results = try simulation.runCorrelated(
inputs: [stock1, stock2],
correlationMatrix: correlation,
iterations: 10_000
) { returns in
// Portfolio return (50/50 allocation)
return 0.5 * returns[0] + 0.5 * returns[1]
}Project Management:
// Correlated task durations (shared resources, dependencies)
let task1 = SimulationInput(name: "Development", distribution: DistributionTriangular(low: 20, high: 40, base: 28))
let task2 = SimulationInput(name: "Testing", distribution: DistributionTriangular(low: 10, high: 25, base: 15))
// Tasks positively correlated (both affected by team availability)
let correlation = [
[1.0, 0.6],
[0.6, 1.0]
]
let projectDuration = try simulation.runCorrelated(
inputs: [task1, task2],
correlationMatrix: correlation,
iterations: 5_000
) { durations in
return durations[0] + durations[1] // Sequential tasks
}Revenue Modeling:
// Multiple correlated revenue streams
let revenue1 = SimulationInput(name: "ProductA", distribution: DistributionNormal(1_000_000, 150_000))
let revenue2 = SimulationInput(name: "ProductB", distribution: DistributionNormal(800_000, 120_000))
let revenue3 = SimulationInput(name: "ProductC", distribution: DistributionNormal(500_000, 80_000))
// Products share market conditions
let correlation = [
[1.0, 0.7, 0.5],
[0.7, 1.0, 0.6],
[0.5, 0.6, 1.0]
]
let totalRevenue = try simulation.runCorrelated(
inputs: [revenue1, revenue2, revenue3],
correlationMatrix: correlation,
iterations: 10_000
) { revenues in
return revenues.reduce(0, +)
}- Production Ready: Full error handling, input validation, edge case coverage
- Mathematically Rigorous: Cholesky decomposition, positive definiteness checking
- Distribution Agnostic: Works with any
DistributionRandomtype - Performance Optimized: Precomputes Cholesky factor, efficient rank transformation
- Well Tested: 39 comprehensive tests with 100% pass rate
- Documentation: Complete DocC comments with examples and use cases
- Swift 6.0 Concurrency: Sendable conformance throughout
- Builds on existing Monte Carlo framework (v1.4.0)
- Uses
correlationCoefficient()from existing statistics module - Leverages
SimulationResults,SimulationInput,SimulationStatistics - Compatible with all 16 distribution types in the library
- MonteCarloSimulation: Added default initializer for use with
runCorrelated()init()creates empty simulation for directrunCorrelated()calls- Maintains backward compatibility with existing
init(iterations:model:)API
Correlation Preservation:
- Iman-Conover method preserves Spearman (rank) correlation
- For normal distributions, Spearman ≈ Pearson correlation
- For non-normal distributions, provides robust rank-based correlation
- Alternative: Gaussian copula would preserve exact Pearson correlation but requires distribution quantile functions
Performance:
- Cholesky decomposition: O(n³) for n variables (computed once)
- Sample generation: O(n²) per iteration (matrix-vector multiplication)
- Rank transformation: O(n × iterations × log(iterations)) for sorting
- Suitable for typical simulation sizes (2-10 variables, 1K-100K iterations)
Numerical Stability:
- Epsilon tolerance (1e-10) for floating-point comparisons
- Validates positive definiteness before attempting Cholesky
- Clamps rank-based indices to valid array bounds
- Handles edge cases (perfect correlation, singular matrices)
Monte Carlo Simulation Framework (Phase 2.1 - Core Engine)
A comprehensive framework for modeling uncertainty and risk in complex systems through Monte Carlo simulation. This release delivers the complete core engine with 5 major components and 68 passing tests.
1. Percentiles (Percentiles.swift - Sources/BusinessMath/Simulation/MonteCarlo/)
Statistical percentile calculations for analyzing simulation result distributions.
- Properties:
p5,p10,p25,p50(median),p75,p90,p95,p99,min,max - Computed property:
interquartileRange(IQR = p75 - p25) - Method:
percentile(_ p: Double) -> Doublefor custom percentiles - Implementation: R-7/Type 7 linear interpolation method (standard in R, NumPy)
- Position = (n - 1) × percentile
- Linear interpolation between data points
- Produces fractional values for accurate quantile estimation
- 12 comprehensive tests covering:
- Sorted/unsorted data initialization
- Small datasets, single values, duplicates
- IQR calculation accuracy
- Custom percentile calculation
- Negative values, large datasets (10K+ values)
- Ordering invariants
- Accuracy with known distributions (uniform, normal)
2. SimulationStatistics (SimulationStatistics.swift)
Complete statistical summary for simulation results including central tendency, dispersion, and shape measures.
- Central tendency:
mean,median - Dispersion:
stdDev,variance,min,max - Shape:
skewness(distribution asymmetry measure) - Confidence intervals:
ci90,ci95,ci99convenience properties - Method:
confidenceInterval(level: Double) -> (low, high)for custom levels - Implementation:
- Sample statistics (n-1 denominator for variance)
- Bias-corrected skewness formula
- Normal approximation for confidence intervals
- Direct calculation (no external dependencies) for performance
- 12 comprehensive tests covering:
- Simple datasets (1-10, 1-100)
- Normal/uniform/exponential distributions (10K samples)
- Confidence interval validation (90%, 95%, 99%)
- Edge cases (single value, all same values)
- Skewness calculation (right/left/symmetric)
- Large datasets (100K values) for performance
3. SimulationInput (SimulationInput.swift)
Type-erased wrapper for uncertain input variables using protocol-based design with type erasure.
- Accepts any
DistributionRandomconforming type (Normal, Uniform, Triangular, Weibull, Beta, etc.) - Accepts custom sampling closures for bespoke distributions
- Properties:
name(String),metadata(dictionary for documentation) - Method:
sample() -> Doublegenerates random samples - Implementation: Type erasure pattern with
@Sendable () -> Doubleclosure- Works with generic
DistributionRandomprotocol vianext()method - Swift 6.0 concurrency-safe (Sendable conformance)
- Zero-cost abstraction (compile-time type erasure)
- Works with generic
- 13 comprehensive tests covering:
- Integration with Normal, Uniform, Triangular, Weibull distributions
- Custom sampling closures (constant, bimodal, time-dependent)
- Metadata handling (optional, custom key-value pairs)
- Sendable conformance for concurrent simulations
- Multiple samples verification (proper randomness)
- Array storage for multi-variable simulations
4. SimulationResults (SimulationResults.swift)
Comprehensive container for simulation outcomes with analysis methods.
- Properties:
values(all outcomes),statistics,percentiles - Probability methods:
probabilityAbove(_ threshold: Double) -> DoubleprobabilityBelow(_ threshold: Double) -> DoubleprobabilityBetween(_ lower: Double, _ upper: Double) -> Double
- Visualization:
histogram(bins: Int) -> [(range, count)] - Confidence intervals:
confidenceInterval(level:)method - Implementation:
- Automatic computation of statistics and percentiles on initialization
- Order-independent
probabilityBetween(handles reversed arguments) - Equal-width histogram binning with full range coverage
- All probability methods use simple counting (non-parametric)
- 15 comprehensive tests covering:
- Basic initialization and property access
- Probability calculations (above/below/between)
- Edge cases (empty ranges, single value, extreme values)
- Histogram generation (5/10/20 bins, coverage validation)
- Confidence intervals (90%, 95%, 99%)
- Integration with real simulations (10K+ iterations)
- Statistics-percentiles consistency validation
5. MonteCarloSimulation (MonteCarloSimulation.swift)
The main simulation engine that orchestrates uncertain inputs and model execution.
- Properties:
iterations(Int),inputs(array of SimulationInput) - Model function:
@Sendable ([Double]) -> Doublecomputes outcomes from inputs - Method:
addInput(_ input: SimulationInput)adds uncertain variables - Method:
run() throws -> SimulationResultsexecutes simulation - Error handling:
SimulationErrorenum (insufficientIterations,noInputs,invalidModel) - Implementation:
- Validates iterations > 0 and inputs non-empty
- Samples from all inputs in order for each iteration
- Validates outcomes (finite, non-NaN, non-Inf)
- Reserves capacity for performance
- Thread-safe design (Sendable throughout)
- 16 comprehensive tests covering:
- Basic initialization and input management
- Simple models (constant, sum, difference)
- Known analytical solutions (sum of normals)
- Real-world models (profit, NPV, PERT estimation)
- Convergence (standard error decreases with iterations)
- Performance (10K iterations < 1 second)
- Error handling (zero iterations, no inputs)
- Edge cases (single iteration, multiple runs)
- Complex multi-variable models (4+ inputs)
- Reliability analysis with Weibull distributions
SimulationError (SimulationError.swift)
Comprehensive error handling for simulation execution.
- Cases:
insufficientIterations,noInputs,invalidModel(iteration, details) - Conforms to
LocalizedErrorfor user-friendly messages - Sendable for thread-safe error propagation
Sendable Conformance added to existing distribution structs for Swift 6.0 concurrency:
DistributionNormalnowSendableDistributionUniformnowSendableDistributionTriangularnowSendableDistributionWeibullnowSendable
New Files:
Sources/BusinessMath/Simulation/MonteCarlo/Percentiles.swift(190 lines)Sources/BusinessMath/Simulation/MonteCarlo/SimulationStatistics.swift(263 lines)Sources/BusinessMath/Simulation/MonteCarlo/SimulationInput.swift(193 lines)Sources/BusinessMath/Simulation/MonteCarlo/SimulationResults.swift(198 lines)Sources/BusinessMath/Simulation/MonteCarlo/MonteCarloSimulation.swift(227 lines)Sources/BusinessMath/Simulation/MonteCarlo/SimulationError.swift(48 lines)Tests/BusinessMathTests/MonteCarlo/PercentilesTests.swift(193 lines, 12 tests)Tests/BusinessMathTests/MonteCarlo/SimulationStatisticsTests.swift(239 lines, 12 tests)Tests/BusinessMathTests/MonteCarlo/SimulationInputTests.swift(237 lines, 13 tests)Tests/BusinessMathTests/MonteCarlo/SimulationResultsTests.swift(243 lines, 15 tests)Tests/BusinessMathTests/MonteCarlo/MonteCarloSimulationTests.swift(291 lines, 16 tests)
Testing:
- Total test count: 68 new tests (12 + 12 + 13 + 15 + 16) across 5 test suites
- All tests passing (100% pass rate)
- Test execution time: ~0.5 seconds for all 68 tests
- Coverage: Comprehensive testing including:
- Edge cases (empty, single value, large datasets)
- Statistical validation (known distributions)
- Convergence verification
- Performance benchmarks (10K-100K iterations)
- Error handling (all error paths tested)
- Integration tests (complete workflows)
Code Quality:
- No breaking changes - fully backward compatible with v1.0.0-1.3.0
- Zero new compiler warnings
- Full Swift 6.0 concurrency support - Sendable conformance throughout
- Comprehensive DocC documentation - every public API documented with examples
- Test-Driven Development - all tests written before implementation
- Type-safe design - leverages Swift's type system for correctness
- Performance optimized - capacity reservation, direct calculations
Development Approach:
- Test-Driven Development (TDD): Tests written first, then implementation
- Incremental validation: Each component tested independently before integration
- Protocol-based design: Type erasure for flexibility with zero runtime cost
- Sendable-first: All types designed for concurrent execution
Financial Modeling:
var simulation = MonteCarloSimulation(iterations: 10_000) { inputs in
let revenue = inputs[0]
let costs = inputs[1]
return revenue - costs
}
simulation.addInput(SimulationInput(name: "Revenue",
distribution: DistributionNormal(mean: 1_000_000, stdDev: 100_000)))
simulation.addInput(SimulationInput(name: "Costs",
distribution: DistributionNormal(mean: 700_000, stdDev: 50_000)))
let results = try simulation.run()
print("Expected profit: $\(results.statistics.mean)")
print("Risk of loss: \(results.probabilityBelow(0) * 100)%")Project Management (PERT estimation):
var simulation = MonteCarloSimulation(iterations: 5_000) { inputs in
let optimistic = inputs[0]
let mostLikely = inputs[1]
let pessimistic = inputs[2]
return (optimistic + 4.0 * mostLikely + pessimistic) / 6.0
}
simulation.addInput(SimulationInput(name: "Optimistic",
distribution: DistributionTriangular(low: 10, high: 15, base: 12)))
simulation.addInput(SimulationInput(name: "MostLikely",
distribution: DistributionTriangular(low: 15, high: 25, base: 20)))
simulation.addInput(SimulationInput(name: "Pessimistic",
distribution: DistributionTriangular(low: 25, high: 40, base: 30)))
let results = try simulation.run()
print("Expected duration: \(results.statistics.mean) days")
print("90% confidence: [\(results.percentiles.p5), \(results.percentiles.p95)]")Reliability Analysis:
var simulation = MonteCarloSimulation(iterations: 5_000) { inputs in
// System fails when first component fails
return min(inputs[0], inputs[1])
}
simulation.addInput(SimulationInput(name: "Component1",
distribution: DistributionWeibull(shape: 2.0, scale: 1000.0)))
simulation.addInput(SimulationInput(name: "Component2",
distribution: DistributionWeibull(shape: 1.5, scale: 1200.0)))
let results = try simulation.run()
print("Expected system life: \(results.statistics.mean) hours")- ✅ Phase 1 (v1.3.0): Beta + Weibull distributions - COMPLETE
- ✅ Phase 2.1 (v1.4.0): Core Monte Carlo engine - COMPLETE
- 📋 Phase 2.2 (v1.4.1): Risk metrics (VaR, CVaR) - PLANNED
- 📋 Phase 2.3 (v1.4.2): Scenario analysis - PLANNED
- 📋 Phase 3 (v1.5.0): Correlated variables - PLANNED
- 📋 Phase 4 (v1.6.0): TimeSeries statistical methods - PLANNED
This release completes the core Monte Carlo simulation framework, providing a production-ready engine for uncertainty modeling and risk analysis. The framework supports arbitrary model complexity, multiple uncertain variables, and comprehensive result analysis.
All components follow Swift 6.0 strict concurrency requirements and are fully thread-safe for parallel execution scenarios.
Risk Metrics for Monte Carlo Simulations (Phase 2.2 - Risk Analysis)
Financial risk metrics for comprehensive risk assessment and regulatory compliance. This release extends the Monte Carlo framework with industry-standard risk measures used in portfolio management, capital allocation, and regulatory reporting.
1. Value at Risk (VaR)
Maximum expected loss at a given confidence level, answering: "What is the worst loss we can expect with X% confidence?"
- Method:
valueAtRisk(confidenceLevel: Double) -> DoubleconfidenceLevel: 0.0 to 1.0 (e.g., 0.95 for 95% confidence)- Returns: The loss threshold at the specified confidence level
- Calculation: Percentile-based approach
- 95% VaR = 5th percentile (95% confidence losses won't exceed this)
- 99% VaR = 1st percentile (99% confidence losses won't exceed this)
- Uses R-7/Type 7 linear interpolation for accuracy
- Interpretation:
- Negative values represent losses (most common)
- Positive values represent gains (for profit distributions)
- Higher confidence → more extreme VaR
- Use Cases:
- Portfolio risk management
- Capital requirement calculations (Basel III)
- Risk-adjusted performance measurement
- Stress testing
2. Conditional Value at Risk (CVaR) / Expected Shortfall
Expected loss given that losses exceed the VaR threshold, answering: "If losses exceed our VaR, what is the expected loss?"
- Method:
conditionalValueAtRisk(confidenceLevel: Double) -> DoubleconfidenceLevel: 0.0 to 1.0 (e.g., 0.95 for 95% confidence)- Returns: The expected loss in the tail beyond VaR
- Calculation: Tail mean approach
- Calculate VaR at the given confidence level
- Find all outcomes worse than VaR (in the tail)
- Return the mean of these tail outcomes
- Why CVaR Matters:
- Addresses VaR's key limitation: VaR tells you the threshold but not how bad it gets beyond that
- CVaR tells you the average loss in the worst cases
- CVaR is always ≥ VaR (for losses, meaning more extreme/negative)
- Coherent risk measure: Unlike VaR, satisfies all axioms of coherent risk measures
- Subadditive: Portfolio CVaR ≤ sum of individual CVaRs (encourages diversification)
- Regulatory Context:
- Preferred by many regulators for capital allocation
- Used in Basel III for market risk
- Required by some insurance regulators (Solvency II)
- Use Cases:
- Capital allocation across business units
- Tail risk assessment
- Risk-based pricing
- Scenario analysis
VaR Formula:
VaR_α = inf{x : P(Loss ≤ x) ≥ α}
where α is the confidence level (e.g., 0.95)
CVaR Formula:
CVaR_α = E[Loss | Loss ≥ VaR_α]
Expected loss in the tail beyond VaR
Key Properties:
- CVaR_α ≤ VaR_α (for losses, more negative)
- CVaR approaches minimum as confidence → 1.0
- Both metrics are monotonically increasing in confidence level
- Linear interpolation ensures smooth, continuous estimates
Extension to SimulationResults (RiskMetrics.swift)
All risk metrics are implemented as extensions to SimulationResults, providing seamless integration with existing Monte Carlo simulations.
- File:
Sources/BusinessMath/Simulation/MonteCarlo/RiskMetrics.swift(215 lines) - Architecture: Extension pattern for clean separation of concerns
- Helper method:
calculatePercentile(alpha:)using R-7 interpolation - Consistency: Uses same interpolation method as
Percentilesstruct - Performance: Efficient sorting and filtering operations
- Thread-safety: All methods are Sendable-compatible
Comprehensive Test Suite (RiskMetricsTests.swift)
- File:
Tests/BusinessMathTests/MonteCarlo/RiskMetricsTests.swift(301 lines) - Test count: 15 comprehensive tests
- All tests passing (100% pass rate)
- Test execution time: ~0.25 seconds
Test Coverage:
- VaR calculations at different confidence levels (90%, 95%, 99%)
- Validates against known distributions (N(0,1))
- Verifies VaR increases with confidence level
- CVaR calculations at different confidence levels (95%, 99%)
- Validates against theoretical expectations
- Verifies CVaR is always more extreme than VaR
- Edge cases:
- Single value, two values
- All positive returns, all negative losses
- Extreme confidence levels (50%, 99.9%)
- Distribution validation:
- Normal distribution (N(0,1)): VaR_95% ≈ -1.645
- Uniform distribution (0, 100): easier to validate
- Relationship verification:
- CVaR always ≤ VaR (for losses)
- CVaR approaches minimum at high confidence
- Both metrics consistent across runs
- Real-world scenarios:
- Financial portfolio (60/40 stock/bond)
- Loss scenario (revenue vs costs)
- Integration with complete simulations
Portfolio Risk Management:
// 60/40 stock/bond portfolio
var simulation = MonteCarloSimulation(iterations: 10_000) { inputs in
let stockReturn = inputs[0]
let bondReturn = inputs[1]
return 0.6 * stockReturn + 0.4 * bondReturn
}
simulation.addInput(SimulationInput(name: "Stocks",
distribution: DistributionNormal(mean: 0.12, stdDev: 0.20)))
simulation.addInput(SimulationInput(name: "Bonds",
distribution: DistributionNormal(mean: 0.04, stdDev: 0.05)))
let results = try simulation.run()
let var95 = results.valueAtRisk(confidenceLevel: 0.95)
let cvar95 = results.conditionalValueAtRisk(confidenceLevel: 0.95)
print("95% VaR: \(var95 * 100)%")
print("We are 95% confident losses won't exceed \(abs(var95) * 100)%")
print("95% CVaR: \(cvar95 * 100)%")
print("If losses exceed VaR, expected loss is \(abs(cvar95) * 100)%")
print("Tail risk severity: \(abs(cvar95 - var95) * 100)%")Capital Requirement Calculation:
// Calculate required capital for operational risk
var simulation = MonteCarloSimulation(iterations: 10_000) { inputs in
return inputs[0] // Annual operational losses
}
simulation.addInput(SimulationInput(name: "OpLoss",
distribution: DistributionWeibull(shape: 1.5, scale: 1_000_000)))
let results = try simulation.run()
let var999 = results.valueAtRisk(confidenceLevel: 0.999)
let cvar999 = results.conditionalValueAtRisk(confidenceLevel: 0.999)
print("99.9% VaR: $\(abs(var999))")
print("99.9% CVaR: $\(abs(cvar999))")
print("Recommended capital buffer: $\(abs(cvar999))")Capital Allocation Across Business Units:
// Compare risk of two business units
let results1 = try simulation1.run()
let results2 = try simulation2.run()
let cvar1 = results1.conditionalValueAtRisk(confidenceLevel: 0.99)
let cvar2 = results2.conditionalValueAtRisk(confidenceLevel: 0.99)
// Allocate capital proportional to CVaR
let totalCVaR = abs(cvar1) + abs(cvar2)
let allocation1 = abs(cvar1) / totalCVaR
let allocation2 = abs(cvar2) / totalCVaR
print("Unit 1 capital allocation: \(allocation1 * 100)%")
print("Unit 2 capital allocation: \(allocation2 * 100)%")Risk-Adjusted Performance Measurement:
// Compare two investment strategies
let strategy1Results = try simulation1.run()
let strategy2Results = try simulation2.run()
let var95_1 = strategy1Results.valueAtRisk(confidenceLevel: 0.95)
let var95_2 = strategy2Results.valueAtRisk(confidenceLevel: 0.95)
let return1 = strategy1Results.statistics.mean
let return2 = strategy2Results.statistics.mean
// Risk-adjusted return (return per unit of risk)
let raroc1 = return1 / abs(var95_1)
let raroc2 = return2 / abs(var95_2)
print("Strategy 1 RAROC: \(raroc1)")
print("Strategy 2 RAROC: \(raroc2)")- ✅ Phase 1 (v1.3.0): Beta + Weibull distributions - COMPLETE
- ✅ Phase 2.1 (v1.4.0): Core Monte Carlo engine - COMPLETE
- ✅ Phase 2.2 (v1.4.1): Risk metrics (VaR, CVaR) - COMPLETE
- 📋 Phase 2.3 (v1.4.2): Scenario analysis - PLANNED
- 📋 Phase 3 (v1.5.0): Correlated variables - PLANNED
- 📋 Phase 4 (v1.6.0): TimeSeries statistical methods - PLANNED
- No breaking changes - fully backward compatible with v1.4.0
- Zero new compiler warnings
- Full Swift 6.0 concurrency support - Sendable conformance
- Comprehensive DocC documentation - 200+ lines of documentation
- Test-Driven Development - tests written before implementation
- Industry-standard algorithms - follows Basel III and regulatory guidelines
This release adds critical risk metrics for financial analysis and regulatory compliance. VaR and CVaR are industry-standard measures used by financial institutions worldwide for portfolio management, capital allocation, and regulatory reporting (Basel III, Solvency II).
The implementation uses percentile-based VaR and tail mean CVaR calculations, consistent with industry best practices. Both metrics seamlessly integrate with existing Monte Carlo simulations through extension methods on SimulationResults.
Scenario Analysis Framework (Phase 2.3 - What-If Analysis)
Comprehensive framework for comparing multiple scenarios, performing sensitivity analysis, and identifying key drivers of model outcomes. This release enables strategic planning, stress testing, and data-driven decision making under uncertainty.
1. Scenario (Scenario struct)
Represents a specific set of assumptions for all model inputs, supporting both fixed values and probability distributions.
- Properties:
name: Scenario identifier (e.g., "Base Case", "Best Case", "Worst Case")inputValues: Dictionary of fixed input values (deterministic)inputDistributions: Dictionary of probability distributions (uncertain)
- Builder pattern for configuration:
setValue(_:forInput:)- Set fixed value for an inputsetDistribution(_:forInput:)- Set probability distribution for an input
- Flexible input specification: Mix fixed and uncertain inputs in same scenario
- Type-safe: All inputs validated against model requirements
Example:
let baseCase = Scenario(name: "Base Case") { config in
config.setValue(1_000_000.0, forInput: "Revenue") // Fixed
config.setDistribution(
DistributionNormal(700_000.0, 50_000.0),
forInput: "Costs" // Uncertain
)
}2. ScenarioAnalysis (ScenarioAnalysis struct)
Framework for running and comparing multiple scenarios with the same model.
- Properties:
inputNames: Names of all input variables (defines model interface)iterations: Number of Monte Carlo iterations per scenarioscenarios: Collection of scenarios to analyze
- Methods:
addScenario(_:)- Add a scenario to analyzerun() throws -> [String: SimulationResults]- Execute all scenarios
- Validation:
- Ensures all required inputs are configured
- Detects unknown input names
- Validates scenario consistency
- Error handling:
ScenarioErrorenum with detailed messages - Integration: Seamlessly builds on MonteCarloSimulation framework
Example:
var analysis = ScenarioAnalysis(
inputNames: ["Revenue", "Costs"],
model: { inputs in inputs[0] - inputs[1] },
iterations: 10_000
)
analysis.addScenario(baseCase)
analysis.addScenario(bestCase)
analysis.addScenario(worstCase)
let results = try analysis.run() // Dictionary of results per scenario3. ScenarioComparison (ScenarioComparison struct)
Comparison utilities for analyzing results across scenarios.
- Properties:
results: All scenario resultsscenarioNames: Names of all analyzed scenarios
- Methods:
bestScenario(by:)- Find best scenario by metricworstScenario(by:)- Find worst scenario by metricrankScenarios(by:ascending:)- Sort scenarios by metricsummaryTable(metrics:)- Generate comparison table
- Supported metrics (ScenarioMetric enum):
.mean- Expected value.median- Middle outcome.stdDev- Volatility/uncertainty.p5,.p95- Percentiles.var95,.cvar95- Risk metrics
Example:
let comparison = ScenarioComparison(results: results)
let best = comparison.bestScenario(by: .mean)
print("Best scenario: \(best.name)")
let ranked = comparison.rankScenarios(by: .var95, ascending: true)
// Scenarios sorted by risk (least risky first)
let summary = comparison.summaryTable(metrics: [.mean, .median, .stdDev])
// Tabular comparison of key metrics4. SensitivityAnalysis (SensitivityAnalysis struct)
Framework for identifying which inputs have the greatest impact on outcomes.
- Properties:
inputNames: All input variablesbaseValues: Base case values for sensitivity analysisiterations: Monte Carlo iterations per analysis point
- Methods:
analyzeInput(_:range:steps:)- Analyze single input sensitivitytornadoChart(range:)- Generate tornado diagram data
- Tornado chart: Visual representation of relative input impacts
- Automatically sorted by impact magnitude
- Shows output range for each input variation
- Identifies key drivers vs. minor factors
Example:
let sensitivity = SensitivityAnalysis(
inputNames: ["Revenue", "Costs", "TaxRate"],
model: model,
baseValues: ["Revenue": 1_000_000, "Costs": 700_000, "TaxRate": 0.3],
iterations: 1_000
)
// Tornado chart: which inputs matter most?
let tornado = try sensitivity.tornadoChart(range: 0.9...1.1) // ±10%
for bar in tornado {
print("\(bar.inputName): impact = \(bar.impact)")
}
// Output sorted by impact (largest first)
// Identifies key drivers for focused data collection5. Supporting Types
ScenarioError: Comprehensive error handling.missingInputConfiguration- Input not configured.unknownInput- Invalid input name.noScenarios- No scenarios added
ScenarioConfiguration: Builder class for scenario setupInputSensitivity: Results of single-input sensitivity analysisTornadoBar: Data structure for tornado chart visualization
File: Sources/BusinessMath/Simulation/MonteCarlo/ScenarioAnalysis.swift (490 lines)
- Architecture: Builder pattern for scenario configuration
- Type safety: Generic distribution support with Sendable conformance
- Validation: Comprehensive input validation with clear error messages
- Integration: Built on MonteCarloSimulation for consistency
- Performance: Efficient scenario execution with minimal overhead
Comprehensive Test Suite (ScenarioAnalysisTests.swift)
- File:
Tests/BusinessMathTests/MonteCarlo/ScenarioAnalysisTests.swift(520 lines) - Test count: 16 comprehensive tests
- All tests passing (100% pass rate)
- Test execution time: ~0.06 seconds
Test Coverage:
- Basic functionality:
- Scenario initialization and configuration
- ScenarioAnalysis setup and execution
- Single and multiple scenario analysis
- Scenario types:
- Base/best/worst case analysis
- Fixed values vs. distributions
- Mixed scenarios (some fixed, some uncertain)
- Comparison features:
- Best/worst scenario identification
- Ranking by different metrics
- Summary table generation
- Sensitivity analysis:
- Single input sensitivity
- Tornado chart generation
- Key driver identification
- Stress testing:
- Extreme scenarios (revenue collapse, cost spike)
- Validation of stress test outcomes
- Error handling:
- Missing input configuration
- Unknown input names
- Comprehensive validation
Strategic Planning - Base/Best/Worst Cases:
var analysis = ScenarioAnalysis(
inputNames: ["Revenue", "Costs"],
model: { inputs in inputs[0] - inputs[1] },
iterations: 10_000
)
let baseCase = Scenario(name: "Base Case") { config in
config.setValue(1_000_000.0, forInput: "Revenue")
config.setValue(700_000.0, forInput: "Costs")
}
let bestCase = Scenario(name: "Best Case") { config in
config.setValue(1_200_000.0, forInput: "Revenue")
config.setValue(600_000.0, forInput: "Costs")
}
let worstCase = Scenario(name: "Worst Case") { config in
config.setValue(800_000.0, forInput: "Revenue")
config.setValue(800_000.0, forInput: "Costs")
}
analysis.addScenario(baseCase)
analysis.addScenario(bestCase)
analysis.addScenario(worstCase)
let results = try analysis.run()
let comparison = ScenarioComparison(results: results)
print("Base profit: $\(results["Base Case"]!.statistics.mean)")
print("Best profit: $\(results["Best Case"]!.statistics.mean)")
print("Worst profit: $\(results["Worst Case"]!.statistics.mean)")Uncertainty Analysis - Normal vs. High Volatility:
let normalCase = Scenario(name: "Normal Market") { config in
config.setDistribution(
DistributionNormal(1_000_000.0, 100_000.0),
forInput: "Revenue"
)
config.setDistribution(
DistributionNormal(700_000.0, 50_000.0),
forInput: "Costs"
)
}
let volatileCase = Scenario(name: "Volatile Market") { config in
config.setDistribution(
DistributionNormal(1_000_000.0, 300_000.0), // 3x volatility
forInput: "Revenue"
)
config.setDistribution(
DistributionNormal(700_000.0, 150_000.0),
forInput: "Costs"
)
}
analysis.addScenario(normalCase)
analysis.addScenario(volatileCase)
let results = try analysis.run()
print("Normal risk (95% VaR): \(results["Normal Market"]!.valueAtRisk(0.95))")
print("High risk (95% VaR): \(results["Volatile Market"]!.valueAtRisk(0.95))")Sensitivity Analysis - Identifying Key Drivers:
let model: @Sendable ([Double]) -> Double = { inputs in
let revenue = inputs[0]
let costs = inputs[1]
let taxRate = inputs[2]
return (revenue - costs) * (1.0 - taxRate)
}
let sensitivity = SensitivityAnalysis(
inputNames: ["Revenue", "Costs", "TaxRate"],
model: model,
baseValues: [
"Revenue": 1_000_000.0,
"Costs": 700_000.0,
"TaxRate": 0.3
],
iterations: 1_000
)
let tornado = try sensitivity.tornadoChart(range: 0.9...1.1) // ±10%
print("Input Impact Analysis (sorted by influence):")
for (index, bar) in tornado.enumerated() {
print("\(index + 1). \(bar.inputName): \(bar.impact)")
}
// Use results to prioritize:
// - Data collection efforts (focus on high-impact inputs)
// - Risk mitigation (manage high-impact uncertainties)
// - Negotiation strategies (optimize high-impact parameters)Stress Testing - Extreme Scenarios:
let normal = Scenario(name: "Normal") { config in
config.setValue(1_000_000.0, forInput: "Revenue")
config.setValue(700_000.0, forInput: "Costs")
}
let revenueShock = Scenario(name: "Revenue Collapse") { config in
config.setValue(500_000.0, forInput: "Revenue") // -50%
config.setValue(700_000.0, forInput: "Costs")
}
let costShock = Scenario(name: "Cost Explosion") { config in
config.setValue(1_000_000.0, forInput: "Revenue")
config.setValue(1_100_000.0, forInput: "Costs") // +57%
}
let doubleShock = Scenario(name: "Perfect Storm") { config in
config.setValue(600_000.0, forInput: "Revenue") // -40%
config.setValue(900_000.0, forInput: "Costs") // +29%
}
analysis.addScenario(normal)
analysis.addScenario(revenueShock)
analysis.addScenario(costShock)
analysis.addScenario(doubleShock)
let results = try analysis.run()
// Assess impact of extreme events
for (name, result) in results {
let profit = result.statistics.mean
let riskOfLoss = result.probabilityBelow(0.0)
print("\(name): Profit = $\(profit), P(Loss) = \(riskOfLoss * 100)%")
}- ✅ Phase 1 (v1.3.0): Beta + Weibull distributions - COMPLETE
- ✅ Phase 2.1 (v1.4.0): Core Monte Carlo engine - COMPLETE
- ✅ Phase 2.2 (v1.4.1): Risk metrics (VaR, CVaR) - COMPLETE
- ✅ Phase 2.3 (v1.4.2): Scenario analysis - COMPLETE
- 📋 Phase 3 (v1.5.0): Correlated variables - PLANNED
- 📋 Phase 4 (v1.6.0): TimeSeries statistical methods - PLANNED
- No breaking changes - fully backward compatible with v1.4.1
- Zero new compiler warnings
- Full Swift 6.0 concurrency support - Sendable conformance throughout
- Comprehensive DocC documentation - 490+ lines with examples
- Test-Driven Development - all tests written before implementation
- Builder pattern - Fluent, type-safe scenario configuration
This release completes the core scenario analysis capabilities for the Monte Carlo framework. Organizations can now perform comprehensive "what-if" analysis, compare multiple strategic options, identify key value drivers, and stress test their models under extreme conditions.
The framework is designed for real-world business applications including:
- Strategic planning: Base/best/worst case analysis
- Risk management: Stress testing and extreme scenario analysis
- Investment analysis: Comparing different investment strategies
- Operational planning: Understanding impact of operational uncertainties
- Data prioritization: Identifying which inputs require more precise data
All components integrate seamlessly with the existing Monte Carlo simulation framework, maintaining full backward compatibility while adding powerful new analytical capabilities.
Beta Distribution (CRITICAL - Phase 1 of Monte Carlo Framework)
A continuous probability distribution on [0, 1] for modeling proportions, probabilities, and percentages.
distributionBeta<T: Real>(alpha: T, beta: T) -> TfunctionDistributionBetastruct conforming toDistributionRandomprotocol- 10 comprehensive tests covering:
- Boundary validation (all values in [0, 1])
- Statistical properties (mean validation with various parameters)
- Struct methods (random() and next())
- Symmetric case (α = β)
- Skewed distributions (α > β and α < β)
- Edge cases (small/large parameters, uniform case)
- Implementation: Uses Beta-Gamma relationship with Marsaglia-Tsang method
- X/(X+Y) where X
Gamma(α), YGamma(β) produces Beta(α, β) - Internal
gammaVariate()function supports real-valued shape parameters - Efficient acceptance-rejection sampling for Gamma generation
- X/(X+Y) where X
- Use Cases:
- Project completion percentages
- Market share modeling
- Success rates and probabilities
- Bayesian analysis (conjugate prior for Bernoulli/Binomial)
Weibull Distribution (HIGH - Phase 1 of Monte Carlo Framework)
A flexible continuous distribution widely used in reliability analysis and failure modeling.
distributionWeibull<T: Real>(shape: T, scale: T) -> TfunctionDistributionWeibullstruct conforming toDistributionRandomprotocol- 11 comprehensive tests covering:
- Non-negative value validation
- Statistical properties (mean validation)
- Exponential case (shape = 1)
- Decreasing failure rate (shape < 1, infant mortality)
- Increasing failure rate (shape > 1, wear-out failures)
- Rayleigh-like case (shape = 2)
- Various scale parameters (small, large)
- Large shape parameter (approaches normal)
- Implementation: Inverse transform method
- X = λ × (-ln(1 - U))^(1/k) where U ~ Uniform(0,1)
- Efficient and numerically stable
- Use Cases:
- Equipment failure analysis
- Customer churn timing
- Time-to-event modeling
- Reliability engineering
- Wind speed distributions
New Files:
Sources/BusinessMath/Simulation/distributionBeta.swift(199 lines)Sources/BusinessMath/Simulation/distributionWeibull.swift(157 lines)Tests/BusinessMathTests/Distribution Tests/BetaDistributionTests.swift(186 lines)Tests/BusinessMathTests/Distribution Tests/WeibullDistributionTests.swift(203 lines)
Testing:
- Total test count: 560 tests (539 previous + 10 Beta + 11 Weibull)
- All tests passing
- Test execution time: < 0.1 seconds for new distribution tests
- Comprehensive statistical validation with sampling variance tolerances
Code Quality:
- No breaking changes
- Fully backward compatible with v1.2.0, v1.1.0, and v1.0.0
- Zero new compiler warnings
- Full Swift 6.0 concurrency support (Sendable conformance)
- Comprehensive DocC documentation with examples
Monte Carlo Roadmap Progress:
- ✅ Phase 1 (v1.3.0): Beta + Weibull distributions - COMPLETE
- 📋 Phase 2 (v1.4.0): Monte Carlo simulation framework - PLANNED
- 📋 Phase 3 (v1.5.0): Correlated variables - PLANNED
- 📋 Phase 4 (v1.6.0): TimeSeries statistical methods - PLANNED
Beta Distribution: The implementation uses a sophisticated approach for generating Beta-distributed random values:
- Generate two independent Gamma variates: X ~ Gamma(α, 1) and Y ~ Gamma(β, 1)
- Return X / (X + Y)
- Gamma generation uses Marsaglia-Tsang's method (2000) for shape ≥ 1
- For shape < 1, uses transformation property: Gamma(α+1) × U^(1/α)
This approach is more robust than direct Beta generation methods and handles all parameter ranges efficiently.
Weibull Distribution: The inverse transform method provides:
- Exact sampling (no approximation)
- Efficient computation (single log and power operation)
- Numerical stability across all parameter ranges
- Direct relationship to uniform distribution
Major Performance Optimizations
This release delivers significant performance improvements for Period arithmetic, moving averages, and rolling window operations.
Calendar Caching (5-10x speedup for projections)
- Added cached Calendar instance to avoid repeated
Calendar.currentcalls - Optimized
Period.advanced(by:)- eliminates Calendar creation overhead - Optimized
Period.distance(to:)- uses cached Calendar - Impact: Trend projections 5-10% faster, critical for large forecasts
Sliding Window Optimizations (40% faster for moving averages)
movingAverage()- sliding window with running sum (2-3x faster)rollingSum()- sliding window with running sum (2-3x faster)rollingMin()- eliminated array allocationsrollingMax()- eliminated array allocations- Impact: 12-month moving average on 10K periods: 18s (was 30s) = 40% faster
Improved Operations:
- Moving average (10K periods): 17.9s (was 30.3s) = 40% faster ⚡
- Trend projection (1000 periods): 1.77s (was 1.86s) = 5% faster
- EMA (10K periods): 16.7s (unchanged - not a rolling window operation)
Unchanged Operations (still excellent):
- NPV/IRR/XIRR: < 1ms per operation
- Trend fitting: 40-170ms for 300-1000 points
- Seasonal analysis: 14-160ms for 10 years
- All 539 tests passing
- No breaking changes
- Fully backward compatible with v1.1.0 and v1.0.0
- Zero new compiler warnings
- Optimizations are transparent to users
Before (v1.1.0):
// Created new array for every window position
for i in (window - 1)..<periods.count {
let windowPeriods = Array(periods[(i - window + 1)...i]) // ❌ Allocation
let windowValues = windowPeriods.compactMap { self[$0] }
let sum = windowValues.reduce(T.zero, +)
}After (v1.2.0):
// Maintain running sum, slide window
var windowSum = T.zero
for i in 0..<window { windowSum += values[i] } // Initialize
for i in window..<count {
windowSum -= values[i - window] // Remove old
windowSum += values[i] // Add new
} // ✅ No allocationsBayes' Theorem Implementation
- New
bayes(_:_:_:)function for calculating posterior probabilities - Comprehensive DocC documentation with medical test example
- Formula: P(D|T) = [P(T|D) × P(D)] / [P(T|D) × P(D) + P(T|¬D) × P(¬D)]
- 5 comprehensive tests covering various scenarios:
- Medical test with 1% disease prevalence
- High prior probability cases
- Perfect test accuracy
- Low prior with imperfect test
- Symmetric cases
Rayleigh Distribution
distributionRayleigh(mean:)function using inverse transform methodDistributionRayleighstruct conforming toDistributionRandomprotocol- Generates non-negative random values from Rayleigh distribution
- Use cases: modeling magnitude of 2D vectors, radio signal fading
- 3 comprehensive tests:
- Function variant with statistical validation
- Struct variant (random() and next() methods)
- Edge cases with small mean values
- Removed incorrect
import Testingfrom production Bayes.swift - Fixed parameter typo:
probabiityTGivenNotD→probabilityTrueGivenNotD - Removed duplicate function definition in Bayes Tests
- Removed unnecessary
async/awaitfrom Bayes tests - Cleaned up "zzz In Process" directory (NPV now in production)
- Total test count: 539 tests (531 previous + 5 Bayes + 3 Rayleigh)
- All tests passing
- No breaking changes
- Fully backward compatible with v1.0.0
This is the initial production release of BusinessMath, featuring comprehensive business mathematics, time series analysis, and financial modeling capabilities.
PeriodType Enum
- Four period types: daily, monthly, quarterly, annual
- Comparable ordering (daily < monthly < quarterly < annual)
- Period conversion with precise calendar calculations (365.25 days/year)
- Properties:
daysApproximate,monthsEquivalent - Codable, CaseIterable conformance
- 32 comprehensive tests
Period Struct
- Factory methods:
month(year:month:),quarter(year:quarter:),year(_:),day(_:) - Properties:
startDate,endDate,label - Custom formatting via DateFormatter
- Period subdivision:
months(),quarters(),days() - Type-first comparison for consistent sorting
- Precondition validation (month 1-12, quarter 1-4)
- Sendable conformance for Swift 6 concurrency
- 56 comprehensive tests
Period Arithmetic
- Strideable conformance enabling ranges:
jan...dec - Operators:
Period + Int,Period - Int - Methods:
distance(to:),advanced(by:),next() - Handles month boundaries, year boundaries, and leap years correctly
- 46 comprehensive tests
FiscalCalendar Struct
- Support for custom fiscal year-ends (Apple, Australia, UK, etc.)
- Methods:
fiscalYear(for:),fiscalQuarter(for:),fiscalMonth(for:),periodInFiscalYear(_:) - MonthDay helper struct with validation
- Static
standardproperty for calendar year (Dec 31) - Sendable, Codable, Equatable conformance
- 40 comprehensive tests
TimeSeries Struct
- Generic container:
TimeSeries<T: Real & Sendable> - Initializers:
init(periods:values:),init(data:)with automatic sorting - Duplicate period handling (keeps last value)
- Subscript access with optional and default value variants
- Properties:
valuesArray,count,first,last,isEmpty range(from:to:)for subset extraction- Sequence conformance for iteration and standard library operations
- TimeSeriesMetadata for descriptive information
- Sendable conformance for thread safety
- 38 comprehensive tests (37 passing, 1 skipped due to Swift limitation)
Time Series Operations
- Transformations:
mapValues(_:),filterValues(_:),zip(with:_:) - Filling:
fillForward(over:),fillBackward(over:),fillMissing(with:over:),interpolate(over:) - Aggregation:
aggregate(to:method:)with six methods (sum, average, first, last, min, max) - Supports monthly → quarterly → annual aggregation
- Period alignment in binary operations (intersection)
- 23 comprehensive tests
Time Series Analytics
- Growth analysis:
growthRate(lag:),cagr(from:to:years:) - Moving averages:
movingAverage(window:),exponentialMovingAverage(alpha:) - Cumulative operations:
cumulative(),rollingSum(window:),rollingMin(window:),rollingMax(window:) - Changes:
diff(lag:),percentChange(lag:) - All operations preserve metadata
- 25 comprehensive tests
Present Value Functions
presentValue(futureValue:rate:periods:)- Single amount PVpresentValueAnnuity(payment:rate:periods:type:)- Annuity PV with ordinary/due- AnnuityType enum (ordinary, due)
- Handles edge cases: zero rate, zero periods, negative rates (deflation)
- Comprehensive DocC with formulas and real-world examples
- 25 comprehensive tests
Future Value Functions
futureValue(presentValue:rate:periods:)- Single amount FVfutureValueAnnuity(payment:rate:periods:type:)- Annuity FV with ordinary/due- Reciprocal relationship with present value functions
- Handles edge cases and negative rates
- 28 comprehensive tests
Payment Functions
payment(presentValue:rate:periods:futureValue:type:)- Loan payment calculationprincipalPayment(rate:period:totalPeriods:presentValue:futureValue:type:)- PPMTinterestPayment(rate:period:totalPeriods:presentValue:futureValue:type:)- IPMTcumulativeInterest(rate:startPeriod:endPeriod:totalPeriods:presentValue:futureValue:type:)- CUMIPMTcumulativePrincipal(rate:startPeriod:endPeriod:totalPeriods:presentValue:futureValue:type:)- CUMPRINC- Support for balloon payments via futureValue parameter
- 27 comprehensive tests
IRR Functions
irr(cashFlows:guess:tolerance:maxIterations:)- Internal rate of return via Newton-Raphsonmirr(cashFlows:financeRate:reinvestmentRate:)- Modified IRR- IRRError enum (convergenceFailed, invalidCashFlows, insufficientData)
- Validates cash flows (requires positive and negative)
- Configurable convergence parameters
- 27 comprehensive tests
XNPV/XIRR Functions
xnpv(rate:dates:cashFlows:)- NPV with irregular date intervalsxirr(dates:cashFlows:guess:tolerance:maxIterations:)- IRR with irregular dates- XNPVError enum with comprehensive error handling
- Fractional year calculations (365-day year basis)
- Newton-Raphson method with XNPV derivatives
- 20 comprehensive tests
NPV Functions
npv(discountRate:cashFlows:)- Net present valuenpv(rate:timeSeries:)- TimeSeries variantnpvExcel(rate:cashFlows:)- Excel-compatible NPV (t=1 for first flow)profitabilityIndex(rate:cashFlows:)- PI = (NPV + investment) / investmentpaybackPeriod(cashFlows:)- Simple payback (returns Int?)discountedPaybackPeriod(rate:cashFlows:)- Time-value adjusted payback- Comprehensive documentation explaining differences from Excel
- 46 comprehensive tests
Growth Rate Functions
growthRate(from:to:)- Simple growth ratecagr(beginningValue:endingValue:years:)- Compound annual growth rateapplyGrowth(baseValue:rate:periods:compounding:)- Project future values- CompoundingFrequency enum (annual, semiannual, quarterly, monthly, daily, continuous)
- Handles zero/negative values appropriately
- 33 comprehensive tests
Trend Models
- TrendModel protocol with
fit(to:)andproject(periods:) - LinearTrend: Constant absolute growth (y = mx + b)
- ExponentialTrend: Constant percentage growth (y = a × e^(bx))
- LogisticTrend: S-curve with capacity limit
- CustomTrend: Closure-based for custom functions
- TrendModelError enum (modelNotFitted, insufficientData, invalidData, projectionFailed)
- Sendable conformance throughout
- 20 comprehensive tests
Seasonality Functions
seasonalIndices(timeSeries:periodsPerYear:)- Calculate seasonal factorsseasonallyAdjust(timeSeries:indices:)- Remove seasonalityapplySeasonal(timeSeries:indices:)- Add seasonality backdecomposeTimeSeries(timeSeries:periodsPerYear:method:)- Separate components- DecompositionMethod enum (additive, multiplicative)
- TimeSeriesDecomposition struct (trend, seasonal, residual)
- SeasonalityError enum with comprehensive error handling
- Centered moving average for trend extraction
- 18 comprehensive tests
Integration Tests
- 10 end-to-end workflow tests:
- Complete financial model (NPV, IRR, payback)
- Time series to NPV workflow
- Historical to forecast workflow
- Revenue projection with seasonality
- Monthly to quarterly aggregation
- Multi-year business planning
- Complete investment analysis
- Loan amortization workflow
- Multi-stage growth modeling
- Real estate investment with XIRR
- All tests passing, validating component integration
Documentation Catalog
- 9 comprehensive DocC markdown files (3,676 lines):
- BusinessMath.md: Landing page with navigation
- GettingStarted.md: Comprehensive quickstart (7.3 KB)
- TimeSeries.md: In-depth time series guide (12 KB)
- TimeValueOfMoney.md: Complete TVM reference (15 KB)
- GrowthModeling.md: Forecasting guide (16 KB)
- BuildingRevenueModel.md: Step-by-step tutorial (14 KB)
- LoanAmortization.md: Complete loan analysis (17 KB)
- InvestmentAnalysis.md: Investment evaluation (18 KB)
- Resources/ directory for future enhancements
- Every article includes real-world examples, formulas, and best practices
- Cross-references between related topics
- Hierarchical topic organization
Performance Testing
- 23 performance benchmark tests:
- Large time series creation (10K, 50K periods)
- Time series access patterns (random access, iteration)
- Chained operations on large datasets
- NPV benchmarks (100, 1000 cash flows)
- IRR convergence (10, 50 cash flows)
- XNPV/XIRR with irregular dates
- Trend fitting (linear, exponential, logistic)
- Trend projection (1000 periods)
- Seasonal analysis (indices, adjustment, decomposition)
- Moving average and EMA on large series
- Complete workflow benchmarks
- Memory usage with multiple large series
- PERFORMANCE.md documentation (12 KB):
- Detailed metrics for all operations
- Performance ratings (Excellent/Very Good/Acceptable)
- Real-world performance guidance
- Bottleneck identification
- Optimization recommendations
Swift Features
- Swift 6.0 with strict concurrency checking
- Full Sendable conformance for thread safety
- Generic programming with
Realprotocol from Swift Numerics - Protocol-oriented design (TrendModel, Sequence conformance)
- Swift Testing framework (@Test, #expect syntax)
- DocC documentation throughout
Quality Metrics
- 531 total tests (all passing)
- 19 test suites
- 508 functional tests
- 23 performance tests
- 10 integration tests
- Test-Driven Development (TDD) approach throughout
- No compiler warnings
- Zero known bugs
Performance Characteristics
- NPV/IRR: < 1ms per operation (excellent for real-time)
- Complete forecasts: < 50ms (excellent for interactive use)
- Trend fitting: 40-170ms for 300-1000 points (very good)
- Seasonal decomposition: 14-160ms for 10 years (very good)
- Large time series: O(n²) initialization (acceptable, with optimization opportunities)
Dependencies
- Swift Numerics for
Realprotocol
- Time Series Initialization: O(n²) complexity due to duplicate detection. Optimization opportunity identified (can be reduced to O(n)).
- Period.next(): Uses Calendar.dateComponents each call. Optimization opportunity for monthly periods.
- Large Datasets: Creation of 10K+ period time series takes 20-60s. Acceptable for typical business use (< 1000 periods).
This is the initial release. No migration required.
- ✅ Additional statistical functions (correlation, covariance)
- ✅ Polynomial trend models
- ✅ Monte Carlo simulation framework (with GPU acceleration)
- ✅ CSV/JSON import/export for time series
- Optimize time series initialization (O(n²) → O(n))
- Optimize Period.next() with caching
- Moving average circular buffer implementation
- Hero images for documentation
- Web-hosted documentation export
BusinessMath 1.0.0 is a comprehensive, production-ready library for business mathematics and financial modeling in Swift. Key highlights:
- 📅 Temporal Structures: Complete period types with arithmetic and fiscal calendar support
- 📊 Time Series: Generic container with 20+ operations and analytics functions
- 💰 TVM: All standard financial functions (PV, FV, PMT, NPV, IRR, XIRR)
- 📈 Forecasting: Trend models and seasonal decomposition for complete forecasting workflows
- ✅ Quality: 531 tests, comprehensive documentation, excellent performance
- 🚀 Modern Swift: Swift 6 concurrency, generics, protocol-oriented design
Perfect for:
- Financial analysts building valuation models
- Business planners doing revenue forecasting
- Data scientists analyzing temporal data
- Engineers building financial applications
None (initial release).
None (initial release).
None (initial release - all tests passing).
For detailed implementation history, see 04_IMPLEMENTATION_CHECKLIST.md