// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/CoolantTemperatureMonitor.java
// public class CoolantTemperatureMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getCoolantTemperature();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setCoolantTemperature((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/FuelConsumptionMonitor.java
// public class FuelConsumptionMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getFuelConsumedLastTick();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setFuelConsumption(monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/FuelFertilityMonitor.java
// public class FuelFertilityMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getFuelFertility();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setFuelFertility((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/FuelHeatMonitor.java
// public class FuelHeatMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getFuelHeat();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setFuelHeat((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/MonitorUtils.java
// public class MonitorUtils {
//   private MonitorUtils() { }
// 
//   public static List<SimulationMonitor> instantiate(Collection<? extends SimulationMonitor.Factory> factories) {
//     List<SimulationMonitor> monitors = Lists.newArrayList();
//     for (SimulationMonitor.Factory factory : factories) {
//       monitors.add(factory.create());
//     }
//     return monitors;
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/OutputMonitor.java
// public class OutputMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getEnergyGeneratedLastTick();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setOutput(monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/ReactorHeatMonitor.java
// public class ReactorHeatMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getReactorHeat();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setReactorHeat((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/TimeSeriesSimulationMonitor.java
// public static <T extends TimeSeriesSimulationMonitor> Factory<T> factoryOf(Class<T> klass) {
//   return new Factory<T>(klass);
// }


import java.util.Arrays;
import java.util.List;
import erogenousbeef.bigreactors.api.IHeatEntity;
import erogenousbeef.bigreactors.api.registry.ReactorConversions;
import erogenousbeef.bigreactors.api.registry.ReactorInterior;
import erogenousbeef.bigreactors.api.registry.TurbineCoil;
import erogenousbeef.bigreactors.common.BigReactors;
import erogenousbeef.bigreactors.common.data.StandardReactants;
import erogenousbeef.bigreactors.common.multiblock.helpers.RadiationHelper;
import net.minecraft.item.EnumRarity;
import net.minecraftforge.fluids.Fluid;
import org.sidoh.reactor_simulator.simulator.monitors.CoolantTemperatureMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.FuelConsumptionMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.FuelFertilityMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.FuelHeatMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.MonitorUtils;
import org.sidoh.reactor_simulator.simulator.monitors.OutputMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.ReactorHeatMonitor;
import static org.sidoh.reactor_simulator.simulator.monitors.TimeSeriesSimulationMonitor.Factory.factoryOf;

      if (energyDelta < 0) {
        numNegativeDeltas++;
      }

      if (numNegativeDeltas >= STABILITY_THRESHOLD) {
        break;
      }

      for (SimulationMonitor monitor : monitors) {
        monitor.offer(simulator);
      }

      lastValue = energyValue;
    }

    final ReactorResult result = new ReactorResult();
    for (SimulationMonitor monitor : monitors) {
      monitor.report(result);
    }
    return result;
  }

  public static void main(String[] args) {
    BigReactorSimulator.init();
    String reactor = "OOOOOOOOOORROOOOOOOOOOOOOOOOOOOXXXOOOOOOOOGGXCXGGOOOOOOGGXXXGGOOOOOXXXCXCXXXOOOOXCXXXXXCXOOOOXXXCXCXXXOOOOOGGXXXGGOOOOOOGGXCXGGOOOOOOOOXXXOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO";
    final ReactorDefinition definition = new ReactorDefinition(15, 15, 7, reactor, false, (short)0);

    System.out.println(new LinearControlRodOptimizer(
        ResultMetrics.efficiency(),
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/CoolantTemperatureMonitor.java
// public class CoolantTemperatureMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getCoolantTemperature();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setCoolantTemperature((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/FuelConsumptionMonitor.java
// public class FuelConsumptionMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getFuelConsumedLastTick();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setFuelConsumption(monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/FuelFertilityMonitor.java
// public class FuelFertilityMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getFuelFertility();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setFuelFertility((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/FuelHeatMonitor.java
// public class FuelHeatMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getFuelHeat();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setFuelHeat((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/MonitorUtils.java
// public class MonitorUtils {
//   private MonitorUtils() { }
// 
//   public static List<SimulationMonitor> instantiate(Collection<? extends SimulationMonitor.Factory> factories) {
//     List<SimulationMonitor> monitors = Lists.newArrayList();
//     for (SimulationMonitor.Factory factory : factories) {
//       monitors.add(factory.create());
//     }
//     return monitors;
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/OutputMonitor.java
// public class OutputMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getEnergyGeneratedLastTick();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setOutput(monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/ReactorHeatMonitor.java
// public class ReactorHeatMonitor extends TimeSeriesSimulationMonitor {
//   @Override
//   public double extractValue(MultiblockReactorSimulator simulator) {
//     return simulator.getReactorHeat();
//   }
// 
//   @Override
//   public void report(TimeSeriesMonitor monitor, ReactorResult result) {
//     result.setReactorHeat((float)monitor.getLastMean());
//   }
// }
// 
// Path: src/main/java/org/sidoh/reactor_simulator/simulator/monitors/TimeSeriesSimulationMonitor.java
// public static <T extends TimeSeriesSimulationMonitor> Factory<T> factoryOf(Class<T> klass) {
//   return new Factory<T>(klass);
// }


// Path: src/main/java/org/sidoh/reactor_simulator/simulator/BigReactorSimulator.java
import java.util.Arrays;
import java.util.List;
import erogenousbeef.bigreactors.api.IHeatEntity;
import erogenousbeef.bigreactors.api.registry.ReactorConversions;
import erogenousbeef.bigreactors.api.registry.ReactorInterior;
import erogenousbeef.bigreactors.api.registry.TurbineCoil;
import erogenousbeef.bigreactors.common.BigReactors;
import erogenousbeef.bigreactors.common.data.StandardReactants;
import erogenousbeef.bigreactors.common.multiblock.helpers.RadiationHelper;
import net.minecraft.item.EnumRarity;
import net.minecraftforge.fluids.Fluid;
import org.sidoh.reactor_simulator.simulator.monitors.CoolantTemperatureMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.FuelConsumptionMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.FuelFertilityMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.FuelHeatMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.MonitorUtils;
import org.sidoh.reactor_simulator.simulator.monitors.OutputMonitor;
import org.sidoh.reactor_simulator.simulator.monitors.ReactorHeatMonitor;
import static org.sidoh.reactor_simulator.simulator.monitors.TimeSeriesSimulationMonitor.Factory.factoryOf;


      if (energyDelta < 0) {
        numNegativeDeltas++;
      }

      if (numNegativeDeltas >= STABILITY_THRESHOLD) {
        break;
      }

      for (SimulationMonitor monitor : monitors) {
        monitor.offer(simulator);
      }

      lastValue = energyValue;
    }

    final ReactorResult result = new ReactorResult();
    for (SimulationMonitor monitor : monitors) {
      monitor.report(result);
    }
    return result;
  }

  public static void main(String[] args) {
    BigReactorSimulator.init();
    String reactor = "OOOOOOOOOORROOOOOOOOOOOOOOOOOOOXXXOOOOOOOOGGXCXGGOOOOOOGGXXXGGOOOOOXXXCXCXXXOOOOXCXXXXXCXOOOOXXXCXCXXXOOOOOGGXXXGGOOOOOOGGXCXGGOOOOOOOOXXXOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO";
    final ReactorDefinition definition = new ReactorDefinition(15, 15, 7, reactor, false, (short)0);

    System.out.println(new LinearControlRodOptimizer(
        ResultMetrics.efficiency(),
        new BigReactorSimulator(false, 10000)