Spaces:
Runtime error
Runtime error
| import { calculateAllEmissions } from './carbonCalculator.js'; | |
| /** | |
| * Simulation Service | |
| * Projects future emissions based on behavior change scenarios | |
| */ | |
| /** | |
| * Apply a simulation scenario to the original assessment data and calculate new emissions | |
| * @param {Object} assessmentData - original user inputs | |
| * @param {Object} scenarioParams - changes to apply | |
| * @param {string} scenarioName | |
| * @returns {Object} simulation result | |
| */ | |
| export function runSimulation(assessmentData, scenarioParams, scenarioName) { | |
| // Build modified data by applying scenario params | |
| const modifiedData = applyScenario(assessmentData, scenarioParams); | |
| // Calculate original and projected emissions | |
| const original = calculateAllEmissions(assessmentData); | |
| const projected = calculateAllEmissions(modifiedData); | |
| const originalTotal = original.totalEmission; | |
| const projectedTotal = projected.totalEmission; | |
| const savings = originalTotal - projectedTotal; | |
| const reductionPercentage = | |
| originalTotal > 0 ? parseFloat(((savings / originalTotal) * 100).toFixed(1)) : 0; | |
| return { | |
| scenarioName, | |
| scenarioParams, | |
| originalEmission: originalTotal, | |
| projectedEmission: projectedTotal, | |
| reductionPercentage, | |
| annualSavingsKg: Math.round(savings), | |
| categoryBreakdown: { | |
| original: { | |
| transport: original.transportEmission, | |
| energy: original.energyEmission, | |
| food: original.foodEmission, | |
| shopping: original.shoppingEmission, | |
| }, | |
| projected: { | |
| transport: projected.transportEmission, | |
| energy: projected.energyEmission, | |
| food: projected.foodEmission, | |
| shopping: projected.shoppingEmission, | |
| }, | |
| }, | |
| }; | |
| } | |
| /** | |
| * Apply scenario parameters to original assessment data | |
| * @param {Object} original | |
| * @param {Object} params | |
| * @returns {Object} modified assessment data | |
| */ | |
| function applyScenario(original, params) { | |
| const modified = { ...original }; | |
| // Direct field overrides | |
| if (params.carFuelType !== undefined) modified.carFuelType = params.carFuelType; | |
| if (params.dietType !== undefined) modified.dietType = params.dietType; | |
| if (params.renewablePercentage !== undefined) | |
| modified.renewablePercentage = params.renewablePercentage; | |
| // Reduction factors | |
| if (params.cyclingReductionFactor !== undefined) { | |
| // Reduce daily car km by the cycling reduction factor | |
| modified.dailyCarKm = original.dailyCarKm * (1 - params.cyclingReductionFactor); | |
| modified.cyclingKmPerWeek = | |
| (original.cyclingKmPerWeek || 0) + original.dailyCarKm * params.cyclingReductionFactor * 5; | |
| } | |
| if (params.flightReductionFactor !== undefined) { | |
| modified.shortFlightsPerYear = Math.round( | |
| original.shortFlightsPerYear * (1 - params.flightReductionFactor) | |
| ); | |
| modified.longFlightsPerYear = Math.round( | |
| original.longFlightsPerYear * (1 - params.flightReductionFactor) | |
| ); | |
| } | |
| if (params.electricityReductionFactor !== undefined) { | |
| modified.monthlyElectricityKwh = | |
| original.monthlyElectricityKwh * (1 - params.electricityReductionFactor); | |
| } | |
| if (params.shoppingReductionFactor !== undefined) { | |
| modified.clothingItemsPerYear = Math.round( | |
| original.clothingItemsPerYear * (1 - params.shoppingReductionFactor) | |
| ); | |
| modified.electronicsItemsPerYear = Math.round( | |
| original.electronicsItemsPerYear * (1 - params.shoppingReductionFactor) | |
| ); | |
| } | |
| return modified; | |
| } | |
| /** | |
| * Run multiple simulations and return ranked results | |
| * @param {Object} assessmentData | |
| * @param {Array} scenarios | |
| * @returns {Array} sorted simulation results | |
| */ | |
| export function runMultipleSimulations(assessmentData, scenarios) { | |
| const results = scenarios.map(({ name, params }) => runSimulation(assessmentData, params, name)); | |
| return results.sort((a, b) => b.annualSavingsKg - a.annualSavingsKg); | |
| } | |