CJahns commited on
Commit
02b8818
·
1 Parent(s): ca34550

Upload app.py

Browse files
Files changed (1) hide show
  1. app.py +186 -124
app.py CHANGED
@@ -25,196 +25,258 @@ import streamlit as st
25
  # %%
26
 
27
  url_excel = r'Input_Jahr_2021.xlsx'
 
28
 
29
 
 
 
 
30
 
31
- # %% [markdown]
32
- # Read Sets
33
 
34
- # %%
35
- # Define all sets for the model
36
 
37
- df_excel= pd.read_excel(url_excel,header=None)
38
- t = pd.Index(df_excel.iloc[:,0], name = 't')[0:400]
39
 
40
- df_excel= pd.read_excel(url_excel,header=None, sheet_name = 'Regionen')
41
- r = pd.Index(df_excel.iloc[:,0], name='r')
42
- rr = r.copy()
43
- rr.names = ['rr']
44
 
45
- df_excel= pd.read_excel(url_excel,header=None, sheet_name = 'Regionen')
46
- r = pd.Index(df_excel.iloc[:,0], name='r')
47
 
48
- df_excel = pd.read_excel(url_excel, sheet_name = 'Kraftwerke')
 
 
 
 
 
 
 
 
49
  i = pd.Index(df_excel.iloc[:,0], name = 'i')
 
50
 
51
- df_excel = pd.read_excel(url_excel, sheet_name = 'Kraftwerke')
52
- iConv = pd.Index(df_excel.iloc[1:6,2], name = 'iConv')
53
 
54
- df_excel = pd.read_excel(url_excel, sheet_name = 'Kraftwerke')
55
  iRes = pd.Index(df_excel.iloc[0:4,4], name = 'iRes')
56
 
57
- df_excel = pd.read_excel(url_excel, sheet_name = 'Kraftwerke')
58
- iStor = pd.Index(df_excel.iloc[0:1,6], name = 'iStor')
59
-
60
 
 
 
61
 
 
 
62
 
63
  # %%
 
 
 
 
64
 
65
- ### Parameter
66
  dt = 1
67
 
68
- df_excel= pd.read_excel(url_excel,sheet_name = 'Nachfrage')
69
- df_melt = pd.melt(df_excel,id_vars='Zeit')
70
-
71
- df_melt = df_melt.rename({'Zeit':'t', 'variable':'r'}, axis= 1)
72
- df_melt = df_melt.set_index(['t','r'])
73
-
74
- xr_D_t_r = df_melt.iloc[:,0].to_xarray()
75
-
76
-
77
 
 
 
 
 
 
 
 
78
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
79
 
 
 
 
 
 
 
 
80
 
81
- # %%
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
82
 
83
- ##variable Kosten
84
- df_excel = pd.read_excel(url_excel, sheet_name = 'Kosten')
85
- df_excel = df_excel.rename(columns = {'Konventionelle':'i', 'Unnamed: 1':'Costs'})
86
- df_excel = i.to_frame().reset_index(drop=True).merge( df_excel, how = 'left')
87
  df_excel = df_excel.fillna(0)
88
  df_excel = df_excel.set_index('i')
89
- c_var_i = df_excel.iloc[:,0].to_xarray()
90
 
 
 
 
 
 
 
91
 
92
- ##fixed generation of Res
93
- df_excel = pd.read_excel(url_excel, sheet_name = 'EE',header=[0,1])
 
94
 
95
- #Die Tabelle enthällt 2 Überschriften, deshalb die Anpassung mit stack
96
- df_test = df_excel.set_index([('Zeit', 'Unnamed: 0_level_1')]).stack().stack()
97
- df_test.index = df_test.index.set_names(['t','i','r'])
98
- s_t_r_iRes = df_test.to_xarray()
99
 
100
- s_t_r_iRes.sel(i = ['RoR']).values = 0.8 * s_t_r_iRes.sel(i = ['RoR']).values
 
 
 
 
101
 
 
102
 
103
- #Korrektur: In BE und NL kompletter Zufluss für RoR
104
- f_t_r_i = 0.2/0.8 * s_t_r_iRes.sel(i = ['RoR'])
105
- f_t_r_i['i'].values[0] = 'HydroReservior'
106
 
107
- f_t_r_i.loc[dict(r='BE')] = f_t_r_i.loc[dict(r='BE')]*0
108
- f_t_r_i.loc[dict(r='NL')] = f_t_r_i.loc[dict(r='NL')]*0
 
109
 
 
 
110
 
 
 
111
 
112
- ## y_max
113
- df_excel = pd.read_excel(url_excel, sheet_name = 'InstallierteLeistungen', nrows = 12, usecols = 'A:G')
114
- df_melt2 = pd.melt(df_excel,id_vars='2021 in MW')
115
 
116
- df_melt2 = df_melt2.rename({'2021 in MW' : 'i', 'variable' : 'r'}, axis = 1)
117
- df_melt2 = df_melt2.set_index(['i','r'])
118
 
119
- y_max_i_r = df_melt2.iloc[:,0].to_xarray()
 
120
 
 
 
121
 
122
- ##l_max
123
- df_excel = pd.read_excel(url_excel, sheet_name = 'InstallierteLeistungen', skiprows = range(15), nrows = 1, usecols = 'A:G')
124
- df_excel = df_excel.rename(columns = {'ReservoirSize (geschätzt)' : 'i'})
125
- df_melt3 = pd.melt(df_excel, id_vars = 'i')
126
- df_melt3 = df_melt3.rename({'variable' : 'r'}, axis = 1)
127
- df_melt3 = df_melt3.set_index(['r','i'])
128
- l_max_iStor_r = df_melt3.iloc[:, 0].to_xarray()
129
 
130
- ## inflow of water reservoir
131
- f_t_r_HydroReservoir = 0.2 * s_t_r_iRes.sel(i = ['RoR']) * y_max_i_r.sel(i = ['RoR'])
132
 
 
 
133
 
134
- ##transmission capacity between region r and region rr
135
- df_excel = pd.read_excel(url_excel, sheet_name = 'NTC', skiprows = range (1), nrows = 7, usecols = 'B:H')
136
- df_melt4 = pd.melt(df_excel, id_vars = 'Unnamed: 1')
137
- df_melt4 = df_melt4.rename({'Unnamed: 1' : 'rr' , 'variable' : 'r'}, axis = 1)
138
- df_melt4 = df_melt4.set_index(['r','rr'])
139
- x_cap_r_rr = df_melt4.iloc[:, 0].to_xarray()
140
 
141
- #df_excel.loc[iConv]
142
 
143
 
144
 
 
 
145
 
146
  # %%
147
 
148
- ###Variablen
149
- m = Model()
150
- k = m.add_variables(coords = [t,r], name = 'k', lower = 0)#Curtailment
151
- x = m.add_variables(coords = [t,r,rr], name = 'x', lower = 0)
152
- y = m.add_variables(coords = [t,r,i], name = 'y', lower = 0)
153
- l = m.add_variables(coords = [t,r,i], name = 'l', lower = 0)
154
-
155
- C_op = m.add_variables(name = 'C_op')
156
- eta_x = 0.001
157
- ############## Start with the model
158
-
159
- ##objective function
160
- C_op = (y * c_var_i * dt).sum()
161
-
162
- m.add_objective(C_op)
163
- ##load serving
164
- load_t_r = m.add_constraints((y * dt).sum(dims = 'i') - (k * dt) + \
165
- (-x.sum('rr') + x.sum('r').rename({'rr':'r'}) ) *(1 -eta_x)== xr_D_t_r,name = 'load')
166
- ##maximum capacity limit
167
- maxcap_i_r_t = m.add_constraints((y <= y_max_i_r),name = 'max_cap')
168
- ##infeed of renewables
169
- infeed_iRes_r_t = m.add_constraints((y.sel(i = iRes) <= s_t_r_iRes.sel(i = iRes) * y_max_i_r.sel(i = iRes)),name = 'infeed')
170
- ##capacity restriction storage power plant
171
- maxcapsto_r_iStor_t = m.add_constraints(l.sel(i = iStor) <= l_max_iStor_r, name = 'max. filling str.')
172
- ##transmission capacity
173
- maxcaptrans_r_rr_t = m.add_constraints(x <= x_cap_r_rr, name = 'max. transm. cap.')
174
- ##storage power plant
175
- filling_iStor_r_t = m.add_constraints(l.sel(i = iStor).roll(t = -1) -l.sel(i = iStor) + \
176
- y.sel(i = iStor) * dt == f_t_r_i.sel(i = 'HydroReservior') * dt , name = 'filling level')
177
-
178
-
179
-
180
-
181
-
182
-
183
  # %%
184
 
185
-
186
- m.solve(solver_name = 'highs')
187
-
188
-
189
-
190
-
191
-
192
- # %% [markdown]
193
- # Results
194
 
195
  # %%
 
196
 
 
197
  # Read Objective from solution
198
  m.objective_value
199
 
200
-
201
- #pd.options.plotting.backend = "plotly"
202
  # Read dual values and plot
203
- df = load_t_r.dual.to_dataframe().reset_index()
204
  #df['t'] = pd.to_datetime(df['t'])
 
205
 
206
 
207
  # %%
208
- fig = px.line(df, x='t', y='dual', color='r' )
 
 
 
 
209
 
210
- tab1, tab2 = st.tabs(["Streamlit theme (default)", "Plotly native theme"])
211
- with tab1:
212
- st.plotly_chart(fig, theme="streamlit", use_container_width=True)
213
- with tab2:
214
- st.plotly_chart(fig, theme=None, use_container_width=True)
215
  # %%
 
 
 
 
 
 
 
 
216
 
217
 
218
- # Read values
219
- Productionlevels = m.solution['y'].sel(r = 'DE').to_dataframe()
220
  #Productionlevels
 
25
  # %%
26
 
27
  url_excel = r'Input_Jahr_2021.xlsx'
28
+ url_excel = st.file_uploader()
29
 
30
 
31
+ # %%
32
+ # Slider for gas price [€/MWh_th]
33
+ price_gas = st.slider(value=10, min=0, max=400, label="Natural gas price [€/MWh]", step=10)
34
 
35
+ # Slider for CO2 price [€/t]
36
+ price_co2 = st.slider(value=80, min=0, max=400, label="CO2 price [€/t CO2eq]", step=10)
37
 
38
+ # Slider for CO2 limit [mio. t]
39
+ limit_co2 = st.slider(value=400, min=0, max=750, label="CO2 limit [mio. t]", step=50)
40
 
41
+ # Slider for H2 price / usevalue [€/MWH_th]
42
+ price_h2 = st.slider(value=100, min=0, max=300, label="Hydrogen price [€/MWh]", step=10)
43
 
44
+ # %%
45
+ # Set input file
46
+ url_excel = r'Input_Jahr_2021.xlsx'
 
47
 
48
+ # %% [markdown]
49
+ # Read Sets
50
 
51
+ # %%
52
+ ## Define all sets for the model
53
+ # Timesteps
54
+ df_excel= pd.read_excel(url_excel, sheet_name = 'Timesteps_All', header=None)
55
+ t = pd.Index(df_excel.iloc[:,0], name = 't')[1:168]
56
+ #t = pd.Index(df_excel.iloc[:,0], name = 't')
57
+
58
+ # Technologies
59
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Technologies')
60
  i = pd.Index(df_excel.iloc[:,0], name = 'i')
61
+ i
62
 
63
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Technologies')
64
+ iConv = pd.Index(df_excel.iloc[0:7,2], name = 'iConv')
65
 
66
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Technologies')
67
  iRes = pd.Index(df_excel.iloc[0:4,4], name = 'iRes')
68
 
69
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Technologies')
70
+ iSto = pd.Index(df_excel.iloc[0:2,6], name = 'iSto')
 
71
 
72
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Technologies')
73
+ iPtG = pd.Index(df_excel.iloc[0:1,8], name = 'iPtG')
74
 
75
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Technologies')
76
+ iHyRes = pd.Index(df_excel.iloc[0:1,10], name = 'iHyRes')
77
 
78
  # %%
79
+ ### Parameters
80
+ # CO2 limit (from slider)
81
+ l_co2 = limit_co2.value
82
+ p_co2 = price_co2.value
83
 
84
+ # length of timesteps
85
  dt = 1
86
 
87
+ # Demand
88
+ df_excel= pd.read_excel(url_excel, sheet_name = 'Demand')
89
+ #df_melt = pd.melt(df_excel, id_vars='Zeit')
90
+ df_excel = df_excel.rename(columns = {'Timesteps':'t', 'Unnamed: 1':'Demand'})
91
+ #df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
92
+ df_excel = df_excel.fillna(0)
93
+ df_excel = df_excel.set_index('t')
94
+ D_t = df_excel.iloc[:,0].to_xarray()
 
95
 
96
+ ## Efficiencies
97
+ df_excel = pd.read_excel(url_excel, sheet_name = 'Efficiency')
98
+ df_excel = df_excel.rename(columns = {'All':'i', 'Unnamed: 1':'Efficiency'})
99
+ df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
100
+ df_excel = df_excel.fillna(0)
101
+ df_excel = df_excel.set_index('i')
102
+ eff_i = df_excel.iloc[:,0].to_xarray()
103
 
104
+ ## Variable costs
105
+ # Fuel costs
106
+ df_excel = pd.read_excel(url_excel, sheet_name = 'FuelCosts')
107
+ df_excel = df_excel.rename(columns = {'Conventionals':'i', 'Unnamed: 1':'FuelCosts'})
108
+ df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
109
+ df_excel = df_excel.fillna(0)
110
+ df_excel = df_excel.set_index('i')
111
+ c_fuel_i = df_excel.iloc[:,0].to_xarray()
112
+ # Apply slider value
113
+ c_fuel_i.loc[dict(i = 'Fossil Gas')] = price_gas.value
114
+ c_fuel_i.loc[dict(i = 'H2')] = price_h2.value
115
+
116
+ # Other var. costs
117
+ df_excel = pd.read_excel(url_excel, sheet_name = 'OtherVarCosts')
118
+ df_excel = df_excel.rename(columns = {'Conventionals':'i', 'Unnamed: 1':'OtherVarCosts'})
119
+ df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
120
+ df_excel = df_excel.fillna(0)
121
+ df_excel = df_excel.set_index('i')
122
+ c_other_i = df_excel.iloc[:,0].to_xarray()
123
 
124
+ # Investment costs
125
+ df_excel = pd.read_excel(url_excel, sheet_name = 'InvCosts')
126
+ df_excel = df_excel.rename(columns = {'All':'i', 'Unnamed: 1':'InvCosts'})
127
+ df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
128
+ df_excel = df_excel.fillna(0)
129
+ df_excel = df_excel.set_index('i')
130
+ c_inv_i = df_excel.iloc[:,0].to_xarray()
131
 
132
+ # Emission factor
133
+ df_excel = pd.read_excel(url_excel, sheet_name = 'EmFactor')
134
+ df_excel = df_excel.rename(columns = {'Conventionals':'i', 'Unnamed: 1':'EmFactor'})
135
+ df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
136
+ df_excel = df_excel.fillna(0)
137
+ df_excel = df_excel.set_index('i')
138
+ co2_factor_i = df_excel.iloc[:,0].to_xarray()
139
+
140
+ ## Calculation of variable costs
141
+ c_var_i = (c_fuel_i.sel(i = iConv) + p_co2 * co2_factor_i.sel(i = iConv)) / eff_i.sel(i = iConv) + c_other_i.sel(i = iConv)
142
+
143
+ # RES capacity factors
144
+ #df_excel = pd.read_excel(url_excel, sheet_name = 'RES',header=[0,1])
145
+ #df_excel = pd.read_excel(url_excel, sheet_name = 'RES', index_col=['Timesteps'], columns=['PV', 'WindOn', 'WindOff', 'RoR'])
146
+ df_excel = pd.read_excel(url_excel, sheet_name = 'RES')
147
+ df_excel = df_excel.set_index(['Timesteps'])
148
+ df_test = df_excel
149
+ df_excel = df_excel.stack()
150
+ #df_excel = df_excel.rename(columns={'PV', 'WindOn', 'WindOff', 'RoR'})
151
+ df_test2 = df_excel
152
+ #df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
153
+ #df_excel = df_excel.fillna(0)
154
+
155
+ #df_test = df_excel.set_index(['Timesteps', 'PV', 'WindOn', 'WindOff', 'RoR']).stack([0])
156
+ #df_test.index = df_test.index.set_names(['t','i'])
157
+ s_t_r_iRes = df_excel.to_xarray().rename({'level_1': 'i','Timesteps':'t'})
158
+ #s_t_r_iRes = df_excel.iloc[:,0].to_xarray()
159
+
160
+ # Base capacities
161
+ df_excel = pd.read_excel(url_excel, sheet_name = 'InstalledCap')
162
+ df_excel = df_excel.rename(columns = {'All':'i', 'Unnamed: 1':'InstalledCap'})
163
+ df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
164
+ df_excel = df_excel.fillna(0)
165
+ df_excel = df_excel.set_index('i')
166
+ K_0_i = df_excel.iloc[:,0].to_xarray()
167
 
168
+ # Energy-to-power ratio storages
169
+ df_excel = pd.read_excel(url_excel, sheet_name = 'E2P')
170
+ df_excel = df_excel.rename(columns = {'Storage':'i', 'Unnamed: 1':'E2P ratio'})
171
+ #df_excel = i.to_frame().reset_index(drop=True).merge(df_excel, how = 'left')
172
  df_excel = df_excel.fillna(0)
173
  df_excel = df_excel.set_index('i')
174
+ e2p_iSto = df_excel.iloc[:,0].to_xarray()
175
 
176
+ # Inflow for hydro reservoir
177
+ df_excel = pd.read_excel(url_excel, sheet_name = 'HydroInflow')
178
+ df_excel = df_excel.rename(columns = {'Timesteps':'t', 'Hydro Water Reservoir':'Inflow'})
179
+ df_excel = df_excel.fillna(0)
180
+ df_excel = df_excel.set_index('t')
181
+ h_t = df_excel.iloc[:,0].to_xarray()
182
 
183
+ # %%
184
+ ### Variables
185
+ m = Model()
186
 
187
+ C_tot = m.add_variables(name = 'C_tot') # Total costs
188
+ C_op = m.add_variables(name = 'C_op', lower = 0) # Operational costs
189
+ C_inv = m.add_variables(name = 'C_inv', lower = 0) # Investment costs
 
190
 
191
+ K = m.add_variables(coords = [i], name = 'K', lower = 0) # Endogenous capacity
192
+ y = m.add_variables(coords = [t,i], name = 'y', lower = 0) # Electricity production --> für Elektrolyseure ausschließen
193
+ y_ch = m.add_variables(coords = [t,i], name = 'y_ch', lower = 0) # Electricity consumption --> für alles außer Elektrolyseure und Speicher ausschließen
194
+ l = m.add_variables(coords = [t,i], name = 'l', lower = 0) # Storage filling level
195
+ w = m.add_variables(coords = [t], name = 'w', lower = 0) # RES curtailment
196
 
197
+ ### Model
198
 
199
+ ## Objective function
200
+ C_tot = C_op + C_inv
201
+ m.add_objective(C_tot)
202
 
203
+ ## Costs terms for objective function
204
+ # Operational costs minus revenue for produced hydrogen
205
+ C_op_sum = m.add_constraints((y * c_var_i * dt).sum() - ((y_ch.sel(i = iPtG) / eff_i.sel(i = iPtG)) * price_h2.value * dt).sum() == C_op, name = 'C_op_sum')
206
 
207
+ # Investment costs
208
+ C_inv_sum = m.add_constraints((K * c_inv_i).sum() == C_inv, name = 'C_inv_sum')
209
 
210
+ ## Load serving
211
+ loadserve_t = m.add_constraints(((y * dt).sum(dims = 'i') - (w * dt) == D_t.sel(t = t) * dt), name = 'load')
212
 
213
+ ## Maximum capacity limit
214
+ maxcap_i_t = m.add_constraints((y - K <= K_0_i), name = 'max_cap')
 
215
 
216
+ ## Maximum storage charging and discharging
217
+ maxcha_iSto_t = m.add_constraints((y.sel(i = iSto) + y_ch.sel(i = iSto) - K.sel(i = iSto) <= K_0_i.sel(i = iSto)), name = 'max_cha')
218
 
219
+ ## Maximum electrolyzer capacity
220
+ ptg_prod_iPtG_t = m.add_constraints((y_ch.sel(i = iPtG) - K.sel(i = iPtG)<= K_0_i.sel(i = iPtG)), name = 'max_cha_ptg')
221
 
222
+ ## Infeed of renewables
223
+ infeed_iRes_t = m.add_constraints((y.sel(i = iRes) - s_t_r_iRes.sel(i = iRes).sel(t = t) * K.sel(i = iRes) <= s_t_r_iRes.sel(i = iRes).sel(t = t) * K_0_i.sel(i = iRes)), name = 'infeed')
224
 
225
+ ## Maximum filling level restriction storage power plant --> Energy-to-Power-Ratio eingeführt. (JR)
226
+ maxcapsto_iSto_t = m.add_constraints((l.sel(i = iSto) - K.sel(i = iSto) * e2p_iSto.sel(i = iSto) <= K_0_i.sel(i = iSto) * e2p_iSto.sel(i = iSto)), name = 'max_sto_filling')
 
 
 
 
 
227
 
228
+ ## Filling level restriction hydro reservoir --> Ist Kreisbedingung erfüllt? (JR)
229
+ filling_iHydro_t = m.add_constraints(l.sel(i = iHyRes) - l.sel(i = iHyRes).roll(t = -1) + y.sel(i = iHyRes) * dt == h_t.sel(t = t) * dt, name = 'filling_level_hydro')
230
 
231
+ ## Filling level restriction other storages --> Ist Kreisbedingung erfüllt? (JR)
232
+ filling_iSto_t = m.add_constraints(l.sel(i = iSto) - (l.sel(i = iSto).roll(t = -1) - (y.sel(i = iSto) / eff_i.sel(i = iSto)) * dt + y_ch.sel(i = iSto) * eff_i.sel(i = iSto) * dt) == 0, name = 'filling_level')
233
 
234
+ ## CO2 limit --> ggf. hier auch mit Subset arbeiten (Technologien, die Brennstoff verbrauchen). (JR)
235
+ CO2_limit = m.add_constraints(((y / eff_i) * co2_factor_i * dt).sum() <= l_co2, name = 'CO2_limit')
 
 
 
 
236
 
237
+ m.solve(solver_name = 'highs')
238
 
239
 
240
 
241
+ # %% [markdown]
242
+ # Results
243
 
244
  # %%
245
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
246
  # %%
247
 
248
+ m.solve(solver_name = 'highs',presolve = 'off',run_crossover = 'off',solver = 'ipm')
 
 
 
 
 
 
 
 
249
 
250
  # %%
251
+ #m.solve(solver_name = 'highs', solver = 'ipm', log_file = 'solverlog.txt',run_crossover = 'off' )
252
 
253
+ # %%
254
  # Read Objective from solution
255
  m.objective_value
256
 
257
+ pd.options.plotting.backend = "plotly"
 
258
  # Read dual values and plot
259
+ df = loadserve_t.dual.to_dataframe().reset_index()
260
  #df['t'] = pd.to_datetime(df['t'])
261
+ df
262
 
263
 
264
  # %%
265
+ # Read values
266
+ Productionlevels = m.solution['y'].sel(r = 'DE').to_dataframe().reset_index()
267
+
268
+ df = Productionlevels
269
+ df
270
 
 
 
 
 
 
271
  # %%
272
+ #pandas gui
273
+ # Create Line plot
274
+ fig = px.line(df, x=df['t'], y=df['y'], color = df['i'])
275
+ fig
276
+
277
+ # %%
278
+
279
+
280
 
281
 
 
 
282
  #Productionlevels