diff --git a/VectoCore/VectoCore/Models/Simulation/Impl/PowertrainBuilder.cs b/VectoCore/VectoCore/Models/Simulation/Impl/PowertrainBuilder.cs
index 44e79c8802405c4047bc38b851579c355fd1bae5..52149d3f4c79204f4b2ed6527fb8f7790cf3a881 100644
--- a/VectoCore/VectoCore/Models/Simulation/Impl/PowertrainBuilder.cs
+++ b/VectoCore/VectoCore/Models/Simulation/Impl/PowertrainBuilder.cs
@@ -79,46 +79,62 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 	/// </summary>
 	public static class PowertrainBuilder
 	{
+		private static readonly Dictionary<CycleType, Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>> _builders;
+		
+		private static readonly Dictionary<PowertrainPosition, Func<VectoRunData, VehicleContainer, ElectricSystem, IPowerTrainComponent, IElectricMotor>> _MeasuredSpeedBEVBuilders;
+
+		static PowertrainBuilder()
+		{
+			var pWheelBuilders = new Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>();
+			pWheelBuilders.Add(VectoSimulationJobType.ConventionalVehicle, BuildPWheelConventional);
+			pWheelBuilders.Add(VectoSimulationJobType.BatteryElectricVehicle, BuildPWheelBatteryElectric);
+
+			var measuredSpeedGearBuilders = new Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>();
+			measuredSpeedGearBuilders.Add(VectoSimulationJobType.ConventionalVehicle, BuildMeasuredSpeedGearConventional);
+			measuredSpeedGearBuilders.Add(VectoSimulationJobType.BatteryElectricVehicle, BuildMeasuredSpeedGearBatteryElectric);
+
+			var measuredSpeedBuilders = new Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>();
+			measuredSpeedBuilders.Add(VectoSimulationJobType.ConventionalVehicle, BuildMeasuredSpeedConventional);
+			measuredSpeedBuilders.Add(VectoSimulationJobType.BatteryElectricVehicle, BuildMeasuredSpeedBatteryElectric);
+
+			var vtpBuilders = new Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>();
+			vtpBuilders.Add(VectoSimulationJobType.ConventionalVehicle, BuildVTPConventional);
+
+			var engineOnlyBuilders =  new Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>();
+			engineOnlyBuilders.Add(VectoSimulationJobType.ConventionalVehicle, BuildEngineOnly);
+
+			var distanceBuilders = new Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>();
+			distanceBuilders.Add(VectoSimulationJobType.ConventionalVehicle, BuildFullPowertrainConventional);
+			distanceBuilders.Add(VectoSimulationJobType.ParallelHybridVehicle, BuildFullPowertrainParallelHybrid);
+			distanceBuilders.Add(VectoSimulationJobType.SerialHybridVehicle, BuildFullPowertrainSerialHybrid);
+			distanceBuilders.Add(VectoSimulationJobType.BatteryElectricVehicle, BuildFulPowertrainBatteryElectric);
+			distanceBuilders.Add(VectoSimulationJobType.EngineOnlySimulation, BuildEngineOnly);
+			distanceBuilders.Add(VectoSimulationJobType.IEPC_E, BuildFullPowertrainIEPCE);
+			distanceBuilders.Add(VectoSimulationJobType.IEPC_S, BuildFullPowertrainIEPCSerial);
+
+			_builders = new Dictionary<CycleType, Dictionary<VectoSimulationJobType, Func<VectoRunData, IModalDataContainer, WriteSumData, IVehicleContainer>>>();
+			_builders.Add(CycleType.PWheel, pWheelBuilders);
+			_builders.Add(CycleType.MeasuredSpeed, measuredSpeedBuilders);
+			_builders.Add(CycleType.MeasuredSpeedGear, measuredSpeedGearBuilders);
+			_builders.Add(CycleType.VTP, vtpBuilders);
+			_builders.Add(CycleType.EngineOnly, engineOnlyBuilders);
+			_builders.Add(CycleType.DistanceBased, distanceBuilders);
+
+			_MeasuredSpeedBEVBuilders = new Dictionary<PowertrainPosition, Func<VectoRunData, VehicleContainer, ElectricSystem, IPowerTrainComponent, IElectricMotor>>();
+			_MeasuredSpeedBEVBuilders.Add(PowertrainPosition.BatteryElectricE2, BuildMeasuredSpeedForBEV2);
+			_MeasuredSpeedBEVBuilders.Add(PowertrainPosition.BatteryElectricE3, BuildMeasuredSpeedForBEV3);
+			_MeasuredSpeedBEVBuilders.Add(PowertrainPosition.BatteryElectricE4, BuildMeasuredSpeedForBEV4);
+        }
 
 		public static IVehicleContainer Build(VectoRunData data, IModalDataContainer modData, ISumData sumWriter = null)
 		{
-			switch (data.Cycle.CycleType) {
-				case CycleType.DistanceBased:
-					switch (data.JobType) {
-						case VectoSimulationJobType.ConventionalVehicle: return BuildFullPowertrainConventional(data, modData, sumWriter);
-						case VectoSimulationJobType.ParallelHybridVehicle: return BuildFullPowertrainParallelHybrid(data, modData, sumWriter);
-						case VectoSimulationJobType.SerialHybridVehicle: return BuildFullPowertrainSerialHybrid(data, modData, sumWriter);
-						case VectoSimulationJobType.BatteryElectricVehicle: return BuildFulPowertrainBatteryElectric(data, modData, sumWriter);
-						case VectoSimulationJobType.EngineOnlySimulation: return BuildEngineOnly(data, modData, sumWriter);
-						case VectoSimulationJobType.IEPC_E: return BuildFullPowertrainIEPCE(data, modData, sumWriter);
-						case VectoSimulationJobType.IEPC_S: return BuildFullPowertrainIEPCSerial(data, modData, sumWriter);
-						default: throw new ArgumentOutOfRangeException($"Powertrain Builder cannot build Powertrain for JobType: {data.JobType}");
-					}
-				case CycleType.EngineOnly: return BuildEngineOnly(data, modData, sumWriter);
-				case CycleType.PWheel:
-					switch (data.JobType)
-					{
-						case VectoSimulationJobType.ConventionalVehicle: return BuildPWheelConventional(data, modData, sumWriter);
-						case VectoSimulationJobType.BatteryElectricVehicle: return BuildPWheelBatteryElectric(data, modData, sumWriter);
-						default: throw new ArgumentOutOfRangeException($"Powertrain Builder cannot build Powertrain for JobType: {data.JobType}");
-					}
-				case CycleType.VTP: return BuildVTP(data, modData, sumWriter);
-				case CycleType.MeasuredSpeed:
-					switch (data.JobType)
-					{
-						case VectoSimulationJobType.ConventionalVehicle: return BuildMeasuredSpeedConventional(data, modData, sumWriter);
-						case VectoSimulationJobType.BatteryElectricVehicle: return BuildMeasuredSpeedBatteryElectric(data, modData, sumWriter);
-						default: throw new ArgumentOutOfRangeException($"Powertrain Builder cannot build Powertrain for JobType: {data.JobType}");
-					}
-				case CycleType.MeasuredSpeedGear:
-					switch (data.JobType)
-					{
-						case VectoSimulationJobType.ConventionalVehicle: return BuildMeasuredSpeedGearConventional(data, modData, sumWriter);
-						case VectoSimulationJobType.BatteryElectricVehicle: return BuildMeasuredSpeedGearBatteryElectric(data, modData, sumWriter);
-						default: throw new ArgumentOutOfRangeException($"Powertrain Builder cannot build Powertrain for JobType: {data.JobType}");
-					}
-				default: throw new VectoException("Powertrain Builder cannot build Powertrain for CycleType: {0}", data.Cycle.CycleType);
-			}
+			var cycleType = data.Cycle.CycleType;	
+
+			if (!_builders.ContainsKey(cycleType) || !_builders[cycleType].ContainsKey(data.JobType)) {
+				throw new ArgumentException($"Powertrain Builder: cannot build {cycleType} powertrain for job type: {data.JobType}");
+            }
+
+			return _builders[cycleType][data.JobType].Invoke(data, modData, sumWriter);
 		}
 
 		/// <summary>
@@ -152,23 +168,41 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 			new DummyDriverInfo(container);
 
 			return container;
+        }
+
+        private static IVehicleContainer BuildForCycle(CycleType cycleType, VectoRunData data, IModalDataContainer modData, WriteSumData sumWriter)
+        {
+			VerifyCycleType(data, cycleType);
+
+			if (!_builders.ContainsKey(cycleType) ||  !_builders[cycleType].ContainsKey(data.JobType)) {
+				throw new ArgumentException($"Powertrain Builder: cannot build {cycleType} powertrain for job type: {data.JobType}");
+            }
+
+			return _builders[cycleType][data.JobType].Invoke(data, modData, sumWriter);
 		}
 
-		/// <summary>
-		/// Builds a PWheel powertrain.
-		/// <code>
-		/// PWheelCycle
-		/// â””AxleGear
-		///  ├(Angledrive)
-		///  ├(TransmissionOutputRetarder)
-		///  â””CycleGearbox
-		///   ├(TransmissionInputRetarder)
-		///   â””Clutch
-		///    â””StopStartCombustionEngine
-		///     â””(Aux)
-		/// </code>
-		/// </summary>
-		private static IVehicleContainer BuildPWheelConventional(VectoRunData data, IModalDataContainer modData, ISumData _sumWriter)
+		private static void VerifyCycleType(VectoRunData data, CycleType cycleType)
+        {
+			if (data.Cycle.CycleType != cycleType) {
+				throw new VectoException("CycleType must be {cycleType}.");
+			}
+		}
+
+        /// <summary>
+        /// Builds a PWheel powertrain.
+        /// <code>
+        /// PWheelCycle
+        /// â””AxleGear
+        ///  ├(Angledrive)
+        ///  ├(TransmissionOutputRetarder)
+        ///  â””CycleGearbox
+        ///   ├(TransmissionInputRetarder)
+        ///   â””Clutch
+        ///    â””StopStartCombustionEngine
+        ///     â””(Aux)
+        /// </code>
+        /// </summary>
+        private static IVehicleContainer BuildPWheelConventional(VectoRunData data, IModalDataContainer modData, ISumData _sumWriter)
 		{
 			if (_sumWriter == null)
 				throw new ArgumentNullException(nameof(_sumWriter));
@@ -206,7 +240,7 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 		///     â””(VTPTruckAuxiliaries or VTPBusAuxiliaries)
 		/// </code>
 		/// </summary>
-		private static IVehicleContainer BuildVTP(VectoRunData data, IModalDataContainer modData, ISumData sumWriter)
+		private static IVehicleContainer BuildVTPConventional(VectoRunData data, IModalDataContainer modData, ISumData sumWriter)
 		{
 			if (data.Cycle.CycleType != CycleType.VTP) {
 				throw new VectoException("CycleType must be VTP.");
@@ -277,26 +311,26 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 			}
 
 			engine.Connect(aux.Port());
-		}
-
-		/// <summary>
-		/// Builds a measured speed powertrain.
-		/// <code>
-		/// MeasuredSpeedDrivingCycle
-		/// â””Vehicle
-		///  â””Wheels
-		///   â””Brakes
-		///    â””AxleGear
-		///     ├(Angledrive)
-		///     ├(TransmissionOutputRetarder)
-		///     â””Gearbox, ATGearbox, or APTNGearbox
-		///      ├(TransmissionInputRetarder)
-		///      ├(Clutch)
-		///      â””StopStartCombustionEngine
-		///       â””(Aux)
-		/// </code>
-		/// </summary>
-		private static IVehicleContainer BuildMeasuredSpeedConventional(VectoRunData data, IModalDataContainer modData, ISumData sumWriter)
+        }
+
+        /// <summary>
+        /// Builds a measured speed powertrain.
+        /// <code>
+        /// MeasuredSpeedDrivingCycle
+        /// â””Vehicle
+        ///  â””Wheels
+        ///   â””Brakes
+        ///    â””AxleGear
+        ///     ├(Angledrive)
+        ///     ├(TransmissionOutputRetarder)
+        ///     â””Gearbox, ATGearbox, or APTNGearbox
+        ///      ├(TransmissionInputRetarder)
+        ///      ├(Clutch)
+        ///      â””StopStartCombustionEngine
+        ///       â””(Aux)
+        /// </code>
+        /// </summary>
+        private static IVehicleContainer BuildMeasuredSpeedConventional(VectoRunData data, IModalDataContainer modData, ISumData sumWriter)
 		{
 			if (data.Cycle.CycleType != CycleType.MeasuredSpeed) {
 				throw new VectoException("CycleType must be MeasuredSpeed.");
@@ -317,26 +351,26 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 				.AddComponent(engine, GetIdleController(data.PTO, engine, container))
 				.AddAuxiliaries(container, data);
 			return container;
-		}
-
-		/// <summary>
-		/// Builds a measured speed (with gear) powertrain.
-		/// <code>
-		/// MeasuredSpeedDrivingCycle
-		/// â””Vehicle
-		///  â””Wheels
-		///   â””Brakes
-		///    â””AxleGear
-		///     ├(Angledrive)
-		///     ├(TransmissionOutputRetarder)
-		///     â””CycleGearbox
-		///      ├(TransmissionInputRetarder)
-		///      ├(Clutch)
-		///      â””StopStartCombustionEngine
-		///       â””(Aux)
-		/// </code>
-		/// </summary>
-		private static IVehicleContainer BuildMeasuredSpeedGearConventional(VectoRunData data, IModalDataContainer modData, ISumData sumWriter)
+        }
+
+        /// <summary>
+        /// Builds a measured speed (with gear) powertrain.
+        /// <code>
+        /// MeasuredSpeedDrivingCycle
+        /// â””Vehicle
+        ///  â””Wheels
+        ///   â””Brakes
+        ///    â””AxleGear
+        ///     ├(Angledrive)
+        ///     ├(TransmissionOutputRetarder)
+        ///     â””CycleGearbox
+        ///      ├(TransmissionInputRetarder)
+        ///      ├(Clutch)
+        ///      â””StopStartCombustionEngine
+        ///       â””(Aux)
+        /// </code>
+        /// </summary>
+        private static IVehicleContainer BuildMeasuredSpeedGearConventional(VectoRunData data, IModalDataContainer modData, ISumData sumWriter)
 		{
 			if (data.Cycle.CycleType != CycleType.MeasuredSpeedGear) {
 				throw new VectoException("CycleType must be MeasuredSpeed with Gear.");
@@ -787,8 +821,7 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 		
 		private static IVehicleContainer BuildPWheelBatteryElectric(VectoRunData data, IModalDataContainer modData, WriteSumData sumWriter)
         {
-			if (data.Cycle.CycleType != CycleType.PWheel)
-				throw new VectoException("CycleType must be DistanceBased or MeasuredSpeed");
+			VerifyCycleType(data, CycleType.PWheel);
 			ValidateBatteryElectric(data);
 
 			var container = new VehicleContainer(data.ExecutionMode, modData, sumWriter) { RunData = data };
@@ -926,81 +959,118 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 
 		private static IVehicleContainer BuildMeasuredSpeedBatteryElectric(VectoRunData data, IModalDataContainer modData, WriteSumData sumWriter)
         {
-			if (data.Cycle.CycleType != CycleType.MeasuredSpeed)
-				throw new VectoException("CycleType must be DistanceBased or MeasuredSpeed");
+			VerifyCycleType(data, CycleType.MeasuredSpeed);
 			ValidateBatteryElectric(data);
 
 			var container = new VehicleContainer(data.ExecutionMode, modData, sumWriter) { RunData = data };
-
 			var es = new ElectricSystem(container);
 
-			if (data.BatteryData != null)
-			{
-				var battery = new BatterySystem(container, data.BatteryData);
+			AddBatterySystem<Battery, BatterySystem>(data, container, es);
+			AddSuperCapacitor(data, container, es);
+			AddElectricAuxiliary(data, container, es);
+
+			IPowerTrainComponent powertrain = new MeasuredSpeedDrivingCycle(container, data.Cycle)
+				.AddComponent(new Vehicle(container, data.VehicleData, data.AirdragData))
+				.AddComponent(new Wheels(container, data.VehicleData.DynamicTyreRadius, data.VehicleData.WheelsInertia))
+				.AddComponent(new Brakes(container));
+
+			var position = data.ElectricMachinesData.First().Item1;
+			
+			IElectricMotor em = _MeasuredSpeedBEVBuilders[position].Invoke(data, container, es, powertrain);
+
+			AddBEVBusAuxiliaries(data, container, es, em);
+
+			return container;
+        }
+
+        private static IElectricMotor BuildMeasuredSpeedForBEV2(VectoRunData data, VehicleContainer container, ElectricSystem es, IPowerTrainComponent powertrain)
+        { 
+			var ctl = new BatteryElectricMotorController(container, es);
+			
+			var strategy = (data.GearboxData.Type == GearboxType.APTN) ? 
+				new APTNShiftStrategy(container) : new PEVAMTShiftStrategy(container);
+
+			var gearbox = (data.GearboxData.Type == GearboxType.APTN) ? 
+				(Gearbox) new APTNGearbox(container, strategy) : new PEVGearbox(container, strategy);
+
+			IElectricMotor em = GetElectricMachine(PowertrainPosition.BatteryElectricE2, data.ElectricMachinesData, container, es, ctl);
+
+			powertrain.AddComponent(new AxleGear(container, data.AxleGearData))
+				.AddComponent(gearbox)
+				.AddComponent(em);
+
+			new ATClutchInfo(container);
+
+			return em;
+        }
+
+        private static IElectricMotor BuildMeasuredSpeedForBEV3(VectoRunData data, VehicleContainer container, ElectricSystem es, IPowerTrainComponent powertrain)
+        { 
+			var ctl = new BatteryElectricMotorController(container, es);
+			
+			IElectricMotor em = GetElectricMachine(PowertrainPosition.BatteryElectricE3, data.ElectricMachinesData, container, es, ctl);
+
+			powertrain.AddComponent(new AxleGear(container, data.AxleGearData))
+				.AddComponent(em);
+
+			new DummyGearboxInfo(container);
+			new ATClutchInfo(container);
+			new DummyEngineInfo(container);
+
+			return em;
+        }
+
+        private static IElectricMotor BuildMeasuredSpeedForBEV4(VectoRunData data, VehicleContainer container, ElectricSystem es, IPowerTrainComponent powertrain)
+        {
+			var ctl = new BatteryElectricMotorController(container, es);
+			
+			IElectricMotor em = GetElectricMachine(PowertrainPosition.BatteryElectricE4, data.ElectricMachinesData, container, es, ctl);
+
+			powertrain.AddComponent(em);
+
+			new DummyGearboxInfo(container);
+			new DummyAxleGearInfo(container);
+			new ATClutchInfo(container);
+
+			return em;
+		}
+
+        private static void AddBatterySystem<TBattery, TBatterySystem>(VectoRunData data, VehicleContainer container, ElectricSystem es) 
+			 where TBattery : Battery where TBatterySystem : GenericBatterySystem<TBattery>
+        {
+			if (data.BatteryData != null) {
+				if (data.BatteryData.InitialSoC < data.BatteryData.Batteries.Min(x => x.Item2.MinSOC)) {
+					throw new VectoException("Battery: Initial SoC has to be higher than min SoC");
+				}
+
+				var battery = (TBatterySystem) Activator.CreateInstance(typeof(TBatterySystem), new object[] { container,  data.BatteryData });
 				battery.Initialize(data.BatteryData.InitialSoC);
 				es.Connect(battery);
 			}
+		}
+
+		private static void AddSuperCapacitor(VectoRunData data, VehicleContainer container, ElectricSystem es)
+		{
+			if (data.SuperCapData != null) {
+				if (data.SuperCapData.InitialSoC < data.SuperCapData.MinVoltage / data.SuperCapData.MaxVoltage) {
+					throw new VectoException("SuperCap: Initial SoC has to be higher than min SoC");
+				}
 
-			if (data.SuperCapData != null)
-			{
 				var superCap = new SuperCap(container, data.SuperCapData);
 				superCap.Initialize(data.SuperCapData.InitialSoC);
 				es.Connect(superCap);
 			}
+        }
 
-			var ctl = new BatteryElectricMotorController(container, es);
-
+		private static void AddElectricAuxiliary(VectoRunData data, VehicleContainer container, ElectricSystem es)
+		{
 			var aux = new ElectricAuxiliary(container);
 			aux.AddConstant("P_aux_el", data.ElectricAuxDemand ?? 0.SI<Watt>());
 			es.Connect(aux);
+        }
 
-			var timeBasedCycle = new MeasuredSpeedDrivingCycle(container, data.Cycle);
-			IPowerTrainComponent powertrain = timeBasedCycle
-				.AddComponent(new Vehicle(container, data.VehicleData, data.AirdragData))
-				.AddComponent(new Wheels(container, data.VehicleData.DynamicTyreRadius, data.VehicleData.WheelsInertia))
-				.AddComponent(new Brakes(container));
-
-			IElectricMotor em;
-			var position = data.ElectricMachinesData.First().Item1;
-			switch (position)
-			{
-				case PowertrainPosition.BatteryElectricE4:
-					em = GetElectricMachine(PowertrainPosition.BatteryElectricE4, data.ElectricMachinesData, container, es, ctl);
-					powertrain.AddComponent(em);
-					new DummyGearboxInfo(container);
-					new DummyAxleGearInfo(container);
-					new ATClutchInfo(container);
-					break;
-				case PowertrainPosition.BatteryElectricE3:
-					em = GetElectricMachine(PowertrainPosition.BatteryElectricE3, data.ElectricMachinesData, container, es, ctl);
-					powertrain.AddComponent(new AxleGear(container, data.AxleGearData))
-						.AddComponent(em);
-					new DummyGearboxInfo(container);
-					new ATClutchInfo(container);
-					new DummyEngineInfo(container);
-					break;
-				case PowertrainPosition.BatteryElectricE2 when data.GearboxData.Type != GearboxType.APTN:
-					var strategy = new PEVAMTShiftStrategy(container);
-					em = GetElectricMachine(PowertrainPosition.BatteryElectricE2, data.ElectricMachinesData,
-						container, es, ctl);
-					powertrain.AddComponent(new AxleGear(container, data.AxleGearData))
-						.AddComponent(new PEVGearbox(container, strategy))
-						.AddComponent(em);
-					new ATClutchInfo(container);
-					break;
-				case PowertrainPosition.BatteryElectricE2 when data.GearboxData.Type == GearboxType.APTN:
-					var strategyAPTN = new APTNShiftStrategy(container);
-					em = GetElectricMachine(PowertrainPosition.BatteryElectricE2, data.ElectricMachinesData,
-						container, es, ctl);
-					powertrain.AddComponent(new AxleGear(container, data.AxleGearData))
-						.AddComponent(new APTNGearbox(container, strategyAPTN))
-						.AddComponent(em);
-					new ATClutchInfo(container);
-					break;
-
-				default: throw new ArgumentOutOfRangeException(nameof(position), position, null);
-			}
-
+        private static void AddBEVBusAuxiliaries(VectoRunData data, VehicleContainer container, ElectricSystem es, IElectricMotor em)
+        {
 			if (data.BusAuxiliaries != null)
 			{
 				if (!data.BusAuxiliaries.ElectricalUserInputsConfig.ConnectESToREESS)
@@ -1021,14 +1091,12 @@ namespace TUGraz.VectoCore.Models.Simulation.Impl
 				es.Connect(dcdc);
 				em.BusAux = busAux;
 			}
+		}
 
-			return container;
 
-		}
-		private static IVehicleContainer BuildMeasuredSpeedGearBatteryElectric(VectoRunData data, IModalDataContainer modData, WriteSumData sumWriter)
+        private static IVehicleContainer BuildMeasuredSpeedGearBatteryElectric(VectoRunData data, IModalDataContainer modData, WriteSumData sumWriter)
         {
-			if (data.Cycle.CycleType != CycleType.MeasuredSpeedGear)
-				throw new VectoException("CycleType must be DistanceBased or MeasuredSpeed");
+			VerifyCycleType(data, CycleType.MeasuredSpeedGear);
 			ValidateBatteryElectric(data);
 
 			var container = new VehicleContainer(data.ExecutionMode, modData, sumWriter) { RunData = data };
diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/Battery.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/Battery.cs
index 1661ed67384c8576c9aafcb10725b0f2ce608296..6f78385b7b913e4e1d50cf719a710ec4f93545dc 100644
--- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/Battery.cs
+++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/Battery.cs
@@ -34,7 +34,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 
 		#region Implementation of IElectricEnergyStoragePort
 
-		public void Initialize(double initialSoC)
+		public virtual void Initialize(double initialSoC)
 		{
 			CurrentState.PulseDuration = 0.SI<Second>();
 			PreviousState.PulseDuration = 0.SI<Second>();
@@ -47,7 +47,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 			PreviousState.StateOfCharge = initialSoC;
 		}
 
-		public IRESSResponse Request(Second absTime, Second dt, Watt powerDemand, bool dryRun = false)
+		public virtual IRESSResponse Request(Second absTime, Second dt, Watt powerDemand, bool dryRun = false)
 		{
 			var tPulse = PreviousState.PowerDemand.Sign() == powerDemand.Sign()
 				? PreviousState.PulseDuration
@@ -106,7 +106,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 			};
 		}
 
-		private Ampere SelectSolution(double[] solutions, double sign)
+        protected Ampere SelectSolution(double[] solutions, double sign)
 		{
 			var maxCurrent = Math.Sign(sign) < 0
 				? ModelData.MaxCurrent.LookupMaxDischargeCurrent(PreviousState.StateOfCharge)
@@ -114,7 +114,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 			return solutions.Where(x => Math.Sign(sign) == Math.Sign(x) && Math.Abs(x).IsSmallerOrEqual(Math.Abs(maxCurrent.Value()), 1e-3)).Min().SI<Ampere>();
 		}
 
-		private IRESSResponse PowerDemandExceeded(Second absTime, Second dt, Watt powerDemand, Watt maxDischargePower,
+		protected IRESSResponse PowerDemandExceeded(Second absTime, Second dt, Watt powerDemand, Watt maxDischargePower,
 			Watt maxChargePower, Second tPulse, bool dryRun)
 		{
 			var maxPower = powerDemand < 0 ? maxDischargePower : maxChargePower;
@@ -192,6 +192,8 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 
 		public double StateOfCharge => PreviousState.StateOfCharge;
 
+		public double CalculatedStateOfCharge => PreviousState.CalculatedStateOfCharge;
+
 		public WattSecond StoredEnergy => PreviousState.StateOfCharge * ModelData.Capacity * ModelData.SOCMap.Lookup(PreviousState.StateOfCharge);
 
 		public Watt MaxChargePower(Second dt)
@@ -260,6 +262,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 		public class State
 		{
 			public double StateOfCharge;
+			public double CalculatedStateOfCharge;
 
 			public Second SimulationInterval;
 
diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/BatterySystem.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/BatterySystem.cs
index abd479fe01b31f9df6a95ecacbed5af098328836..6cf7885eca8976b1329ba53397829c44acd78f94 100644
--- a/VectoCore/VectoCore/Models/SimulationComponent/Impl/BatterySystem.cs
+++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/BatterySystem.cs
@@ -14,11 +14,12 @@ using TUGraz.VectoCore.OutputData;
 
 namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 {
-	public class BatterySystem : StatefulVectoSimulationComponent<BatterySystem.State>, IElectricEnergyStorage, IElectricEnergyStoragePort, IUpdateable
+	public class GenericBatterySystem<TBattery> : StatefulVectoSimulationComponent<GenericBatterySystem<TBattery>.State>, 
+		IElectricEnergyStorage, IElectricEnergyStoragePort, IUpdateable where TBattery : Battery
 	{
 		public class BatteryString: IUpdateable
 		{
-			protected readonly List<Battery> _batteries;
+			protected readonly List<TBattery> _batteries;
 			
 			private AmpereSecond _capacity;
 			private AmpereSecond _capacityMinSoc;
@@ -26,12 +27,12 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 
 			public BatteryString()
             {
-				_batteries = new List<Battery>();
+				_batteries = new List<TBattery>();
             }
 
-			public IReadOnlyList<Battery> Batteries => _batteries;
+			public IReadOnlyList<TBattery> Batteries => _batteries;
 
-			public void AddBattery(Battery bat)
+			public void AddBattery(TBattery bat)
 			{
 				_batteries.Add(bat);
 				// Todo: update some properties?
@@ -45,6 +46,9 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 			public AmpereSecond Capacity => _capacity ?? (_capacity = _batteries.Min(x => x.Capacity));
 
 			public double SoC => _batteries.Min(x => x.StateOfCharge * x.Capacity) / Capacity;
+
+			public double CalculatedStateOfCharge => _batteries.Min(x => x.CalculatedStateOfCharge * x.Capacity) / Capacity;
+
 			public WattSecond StoredEnergy => _batteries.Min(x => x.StateOfCharge * x.Capacity) * OpenCircuitVoltage;
 
 			public Watt MaxDischargePower(Second dt, Second tPulse)
@@ -130,10 +134,10 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 		private Scalar _minSoc;
 		private Scalar _maxSoc;
 
-		public BatterySystem(IVehicleContainer dataBus, BatterySystemData batterySystemData) : base(dataBus)
+		public GenericBatterySystem(IVehicleContainer dataBus, BatterySystemData batterySystemData) : base(dataBus)
 		{
 			foreach (var entry in batterySystemData.Batteries) {
-				var bat = new Battery(null, entry.Item2);
+				var bat = (TBattery) Activator.CreateInstance(typeof(TBattery), new object[] { null, entry.Item2 });
 				if (!Batteries.ContainsKey(entry.Item1)) {
 					Batteries[entry.Item1] = new BatteryString();
 				}
@@ -394,7 +398,7 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 		#region Implementation of IUpdateable
 
 		public bool UpdateFrom(object other) {
-			if (other is BatterySystem b) {
+			if (other is GenericBatterySystem<TBattery> b) {
 				PreviousState = b.PreviousState.Clone();
 				return Batteries.All(kv => kv.Value.UpdateFrom(b.Batteries[kv.Key]));
 			}
@@ -403,5 +407,31 @@ namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
 		}
 
 		#endregion
+    }
+
+    public class BatterySystem : GenericBatterySystem<Battery>
+    {
+        public BatterySystem(IVehicleContainer dataBus, BatterySystemData batterySystemData) : base(dataBus, batterySystemData)
+        {
+        }
+    }
+
+    public class IdealBatterySystem : GenericBatterySystem<IdealBattery>
+    { 
+		public IdealBatterySystem(IVehicleContainer dataBus, BatterySystemData batterySystemData) : base(dataBus, batterySystemData)
+        {
+        }
+
+		public override void CommitSimulationStep(Second time, Second simulationInterval, IModalDataContainer container)
+		{
+			base.CommitSimulationStep(time, simulationInterval, container);
+			
+			if (container != null) {
+				container[ModalResultField.REESSStateOfCharge] = CalculatedStateOfCharge.SI();
+			}
+		}
+
+		public double CalculatedStateOfCharge => Batteries.Values.Sum(bs => bs.CalculatedStateOfCharge * bs.Capacity) / TotalCapacity;
 	}
+
 }
\ No newline at end of file
diff --git a/VectoCore/VectoCore/Models/SimulationComponent/Impl/IdealBattery.cs b/VectoCore/VectoCore/Models/SimulationComponent/Impl/IdealBattery.cs
new file mode 100644
index 0000000000000000000000000000000000000000..50df41e03166c6f4bc9eeada0cafadf1665d47e3
--- /dev/null
+++ b/VectoCore/VectoCore/Models/SimulationComponent/Impl/IdealBattery.cs
@@ -0,0 +1,114 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+using TUGraz.VectoCore.Models.Simulation;
+using TUGraz.VectoCore.Models.Simulation.Data;
+using TUGraz.VectoCore.Models.SimulationComponent.Data.Battery;
+using TUGraz.VectoCommon.Utils;
+using TUGraz.VectoCore.OutputData;
+using TUGraz.VectoCommon.Models;
+using TUGraz.VectoCore.Configuration;
+using TUGraz.VectoCore.Models.Connector.Ports.Impl;
+
+namespace TUGraz.VectoCore.Models.SimulationComponent.Impl
+{
+    public class IdealBattery : Battery
+    {
+        public const double IDEAL_STATE_OF_CHARGE = 0.5;
+
+        public IdealBattery(IVehicleContainer container, BatteryData modelData, int idx = -1) : 
+			base(container, modelData, idx)
+        {
+        }
+
+        public override void Initialize(double initialSoC)
+        { 
+            base.Initialize(initialSoC);
+
+            PreviousState.CalculatedStateOfCharge = initialSoC;
+            PreviousState.StateOfCharge = IDEAL_STATE_OF_CHARGE;
+        }
+
+        public override IRESSResponse Request(Second absTime, Second dt, Watt powerDemand, bool dryRun = false)
+		{
+			var tPulse = PreviousState.PowerDemand.Sign() == powerDemand.Sign()
+				? PreviousState.PulseDuration
+				: 0.SI<Second>();
+
+			var maxChargePower = MaxChargePower(dt);
+			var maxDischargePower = MaxDischargePower(dt);
+
+			if (powerDemand.IsGreater(maxChargePower, Constants.SimulationSettings.InterpolateSearchTolerance) ||
+				powerDemand.IsSmaller(maxDischargePower, Constants.SimulationSettings.InterpolateSearchTolerance))
+			{
+				return PowerDemandExceeded(absTime, dt, powerDemand, maxDischargePower, maxChargePower, tPulse, dryRun);
+			}
+
+			var batteryState = ComputeInternalResistanceAndCurrent(PreviousState.StateOfCharge, powerDemand, tPulse);
+			var batteryLoss = batteryState.current * batteryState.internalResistance * batteryState.current;
+			
+			if (dryRun) {
+				return new RESSDryRunResponse(this) {
+					AbsTime = absTime,
+					SimulationInterval = dt,
+					MaxChargePower = maxChargePower,
+					MaxDischargePower = maxDischargePower,
+					PowerDemand = powerDemand,
+					LossPower = batteryLoss,
+					StateOfCharge = IDEAL_STATE_OF_CHARGE
+				};
+			}
+
+			var calcBatteryState = ComputeInternalResistanceAndCurrent(PreviousState.CalculatedStateOfCharge, powerDemand, tPulse);
+			var calcStateOfCharge = CalculateStateOfCharge(ModelData.Capacity * PreviousState.CalculatedStateOfCharge, 
+				calcBatteryState.current, dt);
+
+			CurrentState.SimulationInterval = dt;
+			CurrentState.PowerDemand = powerDemand;
+			CurrentState.TotalCurrent = batteryState.current;
+			CurrentState.BatteryLoss = batteryLoss;
+			CurrentState.StateOfCharge = IDEAL_STATE_OF_CHARGE;
+			CurrentState.CalculatedStateOfCharge = calcStateOfCharge;
+			CurrentState.MaxChargePower = maxChargePower;
+			CurrentState.MaxDischargePower = maxDischargePower;
+
+			return new RESSResponseSuccess(this) {
+				AbsTime = absTime,
+				SimulationInterval = dt,
+				MaxChargePower = maxChargePower,
+				MaxDischargePower = maxDischargePower,
+				PowerDemand = powerDemand,
+				LossPower = batteryLoss,
+				StateOfCharge = IDEAL_STATE_OF_CHARGE
+			};
+        }
+
+		protected (Ohm internalResistance, Ampere current) ComputeInternalResistanceAndCurrent(double stateOfCharge, Watt powerDemand, 
+			Second tPulse)
+		{
+			var internalResistance = ModelData.InternalResistance.Lookup(stateOfCharge, tPulse);
+			
+			var current = powerDemand.IsEqual(0) 
+				? 0.SI<Ampere>() 
+				: SelectSolution(
+					VectoMath.QuadraticEquationSolver(internalResistance.Value(), InternalVoltage.Value(),-powerDemand.Value()),
+					powerDemand.Value());
+
+			return (internalResistance: internalResistance, current: current);
+        }
+
+		protected double CalculateStateOfCharge(AmpereSecond currentCharge, Ampere current, Second dt)
+		{
+			return (currentCharge + current * dt) / ModelData.Capacity;
+        }
+
+        protected override void DoWriteModalResults(Second absTime, Second dt, IModalDataContainer container)
+        {
+            base.DoWriteModalResults(absTime, dt, container);
+            container[ModalResultField.REESSStateOfCharge, BatteryId] = CurrentState.CalculatedStateOfCharge.SI();
+        }
+    }
+}