AN_RB_PLI3.a5.ipynb 18.4 KB
Newer Older
1
2
3
4
5
6
7
{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<h1><center>Analysis of a PLI3.a5 HWC in an RB Circuit</center></h1>\n",
8
    "<img src=\"https://gitlab.cern.ch/LHCData/lhc-sm-hwc/raw/master/figures/rb/RB.png\" width=75%>\n",
9
10
11
    "\n",
    "PLI3.A2 is a simple current cycle at I_INTERM_2 during TIME_INTERM_2, while PLI3.A5 is a current cycle with 2 current levels (I_SM, I_INTERM_2) during TIME_INTERM_2 each. PLI3.A5 can be performed with calorimetric measurement (original purpose). In case of calorimetric measurement, the cryogenic cooling must be stable and maintained constant during the whole cycle. The aim of this test is to check the performance of the current leads and also the splices resistance, and, in case of calorimetric measurements, to detect abnormal heating in the magnets environment.\n",
    "\n",
12
    "<img src=\"https://gitlab.cern.ch/LHCData/lhc-sm-hwc/raw/master/figures/rb/PLI3_current.png\" width=50%>\n",
13
14
15
16
17
    "\n",
    "The required analysis and signatures are listed below.\n",
    "\n",
    "|Responsible|Type of analysis|Criterion|\n",
    "|-----------|----------------|---------|\n",
18
19
20
    "|-|Automatic analysis on earth current and error current|I_EARTH_PLI2_S1 < I_EARTH_MAX and I_ERR_PLI2_S1 < I_ERR_MAX|\n",
    "|MP3|Splice signals|From board A and board B separately R_bus_max <3 nOhm. Individual R_splice_max<0.5nOhm R_mag<50 nOhm|\n",
    "|MP3|Current lead|46 < TT891A < 54K; Abs(U_RES)< 40mV; and no drift Abs(U_HTS) < 0.5mV|\n",
21
22
23
24
25
26
27
28
29
    "\n",
    "source: Powering Procedure and Acceptance Criteria for the 13 kA Dipole Circuits, MP3 Procedure, <a href=\"https://edms.cern.ch/document/874713/5.1\">https://edms.cern.ch/document/874713/5.1</a>"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Analysis Assumptions\n",
30
31
32
    "- We consider standard analysis scenarios, i.e., all signals can be queried. If a signal is missing, an analysis can raise a warning and continue or an error and abort the analysis.\n",
    "- In case a signal is not needed for the analysis, a particular analysis is skipped. In other words, all signals have to be available in order to perform an analysis.\n",
    "- It is recommended to execute each cell one after another. However, since the signals are queried prior to analysis, any order of execution is allowed. In case an analysis cell is aborted, the following ones may not be executed (e.g. I\\_MEAS not present). \n",
33
34
    "\n",
    "# Plot Convention\n",
35
36
    "- Scales are labeled with signal name followed by a comma and a unit in square brackets, e.g., I_MEAS, [A].\n",
    "- If a reference signal is present, it is represented with a dashed line.\n",
37
    "- If the main current is present, its axis is on the left. Remaining signals are attached to the axis on the right. The legend of these signals is located on the lower left and upper right, respectively.\n",
38
39
40
    "- The grid comes from the left axis.\n",
    "- The title contains timestamp, circuit name, and signal name allowing to re-access the signal.\n",
    "- The plots assigned to the left scale have colors: blue (C0) and orange (C1). Plots presented on the right have colors red (C2) and green (C3).\n",
41
    "- Each plot has an individual time-synchronization mentioned explicitly in the description.\n",
42
    "- If an axis has a single signal, then the color of the label matches the signal's color. Otherwise, the label color is black."
43
44
45
46
47
48
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
49
    "# 0. Initialise Working Environment"
50
51
52
53
   ]
  },
  {
   "cell_type": "code",
54
   "execution_count": null,
55
   "metadata": {
56
    "editable": false,
57
58
    "scrolled": false
   },
59
   "outputs": [],
60
   "source": [
Michal Maciejewski's avatar
Michal Maciejewski committed
61
62
    "import io\n",
    "import re\n",
63
    "import sys\n",
64
    "import time\n",
65
    "import pandas as pd\n",
66
67
    "import numpy as np\n",
    "from IPython.display import display, Javascript\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
68
    "from datetime import datetime\n",
69
70
71
72
73
74
    "\n",
    "# lhc-sm-api\n",
    "from lhcsmapi.Time import Time\n",
    "from lhcsmapi.Timer import Timer\n",
    "\n",
    "# GUI\n",
75
    "from lhcsmapi.gui.hwc.HwcSearchModuleMediator import HwcSearchModuleMediator\n",
76
77
78
79
80
    "\n",
    "# Query\n",
    "from lhcsmapi.analysis.RbCircuitQuery import RbCircuitQuery\n",
    "\n",
    "# Analysis\n",
81
    "from lhcsmapi.analysis.report_template import apply_report_template\n",
82
83
    "from lhcsmapi.analysis.RbCircuitAnalysis import RbCircuitAnalysis\n",
    "from lhcsmapi.analysis.busbar.BusbarResistanceAnalysis import convert_to_col\n",
84
    "\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
85
86
    "analysis_start_time = datetime.now().strftime(\"%Y.%m.%d_%H%M%S\")\n",
    "\n",
87
    "import lhcsmapi\n",
88
89
    "print('Analysis executed with lhcsmapi version: {}'.format(lhcsmapi.__version__))\n",
    "\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
90
91
92
    "with io.open(\"../__init__.py\", \"rt\", encoding=\"utf8\") as f:\n",
    "    version = re.search(r'__version__ = \"(.*?)\"', f.read()).group(1)\n",
    "    print('Analysis executed with lhc-sm-hwc notebooks version: {}'.format(version))"
93
94
95
96
97
98
99
100
101
102
103
104
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 1. Select PLI3.a5 HWC Test\n",
    "- Choose a circuit name in order to display HWC test with, campaign name as well as start and end time"
   ]
  },
  {
   "cell_type": "code",
105
   "execution_count": null,
106
   "metadata": {
107
    "editable": false,
Michal Maciejewski's avatar
Michal Maciejewski committed
108
    "scrolled": false
109
   },
110
   "outputs": [],
111
112
113
   "source": [
    "circuit_type = 'RB'\n",
    "hwc_test = 'PLI3.a5'\n",
114
    "hwcb = HwcSearchModuleMediator(circuit_type=circuit_type, hwc_test=hwc_test, hwc_summary_path='/eos/project/l/lhcsm/hwc/HWC_Summary.csv')"
115
116
117
118
119
120
121
122
123
124
125
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 2. Query All Signals Prior to Analysis"
   ]
  },
  {
   "cell_type": "code",
126
   "execution_count": null,
127
128
129
130
131
   "metadata": {
    "tags": [
     "skip_output"
    ]
   },
132
   "outputs": [],
133
134
   "source": [
    "circuit_name = hwcb.get_circuit_name()\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
135
136
    "t_start = Time.to_unix_timestamp(hwcb.get_start_time())\n",
    "t_end = Time.to_unix_timestamp(hwcb.get_end_time())\n",
137
    "is_automatic = hwcb.is_automatic_mode()\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
138
    "rb_query = RbCircuitQuery(circuit_type, circuit_name, max_executions=6)\n",
139
    "rb_analysis = RbCircuitAnalysis(circuit_type, pd.DataFrame(), is_automatic=is_automatic)\n",
140
141
    "\n",
    "with Timer():\n",
142
    "    # PC\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
143
    "    i_meas_nxcals_df = rb_query.query_signal_nxcals(t_start, t_end, t0=t_start, system='PC', signal_names='I_MEAS', spark=spark)[0]\n",
144
    "    i_meas_raw_nxcals_df = rb_query.query_raw_signal_nxcals(t_start, t_end, system='PC', signal_names='I_MEAS', spark=spark)[0]\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
145
    "    plateau_start, plateau_end = rb_analysis.find_plateau_start_and_end(i_meas_raw_nxcals_df, i_meas_threshold=0, min_duration_in_sec=360, time_shift_in_sec=(240, 60))\n",
146
147
    "\n",
    "    # BUSBAR\n",
148
149
150
    "    u_res_feature_df, i_meas_feature_df = rb_query.get_busbar_resistances(Time.to_unix_timestamp(t_start), Time.to_unix_timestamp(t_end), plateau_start, plateau_end, \n",
    "                                                                          signal_name='U_RES', spark=spark)\n",
    "    res_busbar_row_df = rb_analysis.calculate_resistance(i_meas_feature_df, u_res_feature_df, 'U_RES', Time.to_unix_timestamp(t_start), circuit_name)\n",
151
    "    res_busbar_df = convert_to_col(res_busbar_row_df, signal_name='U_RES')\n",
152
    "    \n",
153
    "    # MAGNET\n",
154
155
156
    "    u_mag_feature_df, i_meas_feature_df = rb_query.get_busbar_resistances(Time.to_unix_timestamp(t_start), Time.to_unix_timestamp(t_end), plateau_start, plateau_end, \n",
    "                                                                          signal_name='U_MAG', spark=spark)\n",
    "    res_magnet_row_df = rb_analysis.calculate_resistance(i_meas_feature_df, u_mag_feature_df, 'U_MAG', Time.to_unix_timestamp(t_start), circuit_name)\n",
157
    "    res_magnet_df = convert_to_col(res_magnet_row_df, signal_name='U_MAG')\n",
158
    "    \n",
159
    "    # LEADS\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
160
161
    "    u_res_nxcals_dfs = rb_query.query_signal_nxcals(t_start, t_end, t0=t_start, system=['LEADS_EVEN', 'LEADS_ODD'], signal_names='U_RES', spark=spark)\n",
    "    u_hts_nxcals_dfs = rb_query.query_signal_nxcals(t_start, t_end, t0=t_start, system=['LEADS_EVEN', 'LEADS_ODD'], signal_names='U_HTS', spark=spark)\n",
162
    "\n",
163
164
165
    "    tt891a_nxcals_dfs = rb_query.query_dfb_signal_nxcals(t_start, t_end, system=['LEADS_EVEN_WINCCOA', 'LEADS_ODD_WINCCOA'], signal_names='TT891A', spark=spark)\n",
    "    tt893_nxcals_dfs = rb_query.query_dfb_signal_nxcals(t_start, t_end, system=['LEADS_EVEN_WINCCOA', 'LEADS_ODD_WINCCOA'], signal_names='TT893', spark=spark)\n",
    "    cv891_nxcals_dfs = rb_query.query_dfb_signal_nxcals(t_start, t_end, system=['LEADS_EVEN_WINCCOA', 'LEADS_ODD_WINCCOA'], signal_names='CV891', spark=spark)\n"
166
167
168
169
170
171
172
173
174
175
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 3. Power Converter\n",
    "## 3.1. Plot of the Power Converter Main Current\n",
    "\n",
    "*ANALYSIS*:\n",
176
    "\n",
177
178
    "- Calculation of the duration of current plateaus\n",
    "\n",
179
180
    "*GRAPHS*:\n",
    "\n",
181
182
    "- t = 0 s corresponds to the start of the test\n",
    "- Orange box(es) represent period(s) of time with constant current used for calculation of busbar resistance and DFB thresholds"
183
184
185
186
   ]
  },
  {
   "cell_type": "code",
187
   "execution_count": null,
188
   "metadata": {
189
190
    "deletable": false,
    "editable": false,
191
192
    "scrolled": false
   },
193
   "outputs": [],
194
195
   "source": [
    "ax = i_meas_nxcals_df.plot(figsize=(30, 10), grid=True)\n",
196
197
198
    "for ps, pe in zip(plateau_start, plateau_end):\n",
    "    ax.axvspan(xmin=(ps-Time.to_unix_timestamp(i_meas_raw_nxcals_df.index[0]))/1e9, \n",
    "               xmax=(pe-Time.to_unix_timestamp(i_meas_raw_nxcals_df.index[0]))/1e9, facecolor='xkcd:goldenrod')\n",
199
200
201
202
203
204
205
206
207
208
209
210
211
    "ax.set_xlabel(\"time, [s]\", fontsize=15)\n",
    "ax.set_ylabel(\"I_MEAS, [A]\", fontsize=15)\n",
    "ax.tick_params(labelsize=15)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# 4. Busbar\n",
    "## 4.1. Busbar Resistance\n",
    "\n",
    "*ANALYSIS*:\n",
212
    "\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
213
    "- Calculation of the busbar resistance as the slope of a linear fit of U,I curve obtained from the corresponding mean values of the voltage and current\n",
214
    "\n",
215
216
217
218
219
220
    "*CRITERIA*:\n",
    "\n",
    "- Check if the busbar resistance is below 3 nOhm\n",
    "\n",
    "*GRAPHS*:\n",
    "\n",
221
    "- The busbar resistance, R\n",
222
    "- The green box denotes the validity region of the busbar resostance (0, 3] nOhm"
223
224
225
226
   ]
  },
  {
   "cell_type": "code",
227
   "execution_count": null,
228
229
230
   "metadata": {
    "editable": false
   },
231
   "outputs": [],
232
   "source": [
233
    "res_busbar_outliers_df = rb_analysis.analyze_busbar_magnet_resistance(res_busbar_df, signal_name='R_RES', max_value=3e-9)"
234
235
236
237
   ]
  },
  {
   "cell_type": "code",
238
   "execution_count": null,
239
240
241
242
243
   "metadata": {
    "editable": false
   },
   "outputs": [],
   "source": [
244
    "RbCircuitQuery.query_and_plot_outlier_voltage(res_busbar_outliers_df, t_start, t_end, i_meas_raw_nxcals_df.index[0], plateau_start, plateau_end, spark=spark)"
245
246
   ]
  },
247
248
249
250
251
252
253
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 4.2. Magnet Resistance\n",
    "\n",
    "*ANALYSIS*:\n",
254
    "\n",
255
    "- Calculation of the magnet resistance as the slope of a linear fit of U,I curve obtained from the corresponding mean alues of the voltage and current\n",
256
257
    "\n",
    "*CRITERIA*\n",
258
    "\n",
259
260
261
262
263
    "- Check if the resistance is below 50 nOhm\n",
    "\n",
    "*GRAPHS*:\n",
    "\n",
    "- The magnet resistance, R\n",
264
    "- The green box denotes the validity region of the magnet resistance (0, 50] nOhm\n"
265
266
267
268
   ]
  },
  {
   "cell_type": "code",
269
   "execution_count": null,
270
271
272
   "metadata": {
    "editable": false
   },
273
   "outputs": [],
274
   "source": [
275
    "res_magnet_outliers_df = rb_analysis.analyze_busbar_magnet_resistance(res_magnet_df, signal_name='R_MAG', max_value=50e-9)"
276
277
278
279
   ]
  },
  {
   "cell_type": "code",
280
   "execution_count": null,
281
282
283
284
285
   "metadata": {
    "editable": false
   },
   "outputs": [],
   "source": [
286
    "RbCircuitQuery.query_and_plot_outlier_voltage(res_magnet_outliers_df, t_start, t_end, i_meas_raw_nxcals_df.index[0], plateau_start, plateau_end, spark=spark)"
287
288
   ]
  },
289
290
291
292
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
293
294
    "# 5. DFB\n",
    "## 5.1. DFB Voltage - U_RES\n",
295
    "\n",
296
297
    "*CRITERIA*:\n",
    "- Check if, at constant current, U_RES is constant (no drift < 2mV/h)\n",
298
    "\n",
299
    "*GRAPHS*:\n",
300
    "- t = 0 s corresponds to the start time of the test\n"
301
302
303
304
   ]
  },
  {
   "cell_type": "code",
305
   "execution_count": null,
306
307
308
309
   "metadata": {
    "deletable": false,
    "editable": false
   },
310
   "outputs": [],
311
   "source": [
312
    "RbCircuitAnalysis.assert_u_res_min_max_slope(u_res_nxcals_dfs, plateau_start, plateau_end, Time.to_unix_timestamp(t_start), slope_range=(-2, 2))"
313
314
315
316
317
318
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
319
    "## 5.2. DFB Voltage - U_HTS\n",
320
    "\n",
321
    "*CRITERIA*:  \n",
322
    "- Check if the voltage is below 50% of the threshold -> Abs(U_HTS) < 0.5 mV\n",
323
    "\n",
324
    "*GRAPHS*:\n",
325
    "- t = 0 s corresponds to the start time of the test"
326
327
328
329
   ]
  },
  {
   "cell_type": "code",
330
   "execution_count": null,
331
   "metadata": {
332
333
    "deletable": false,
    "editable": false,
334
335
    "scrolled": false
   },
336
   "outputs": [],
337
   "source": [
338
    "RbCircuitAnalysis.assert_u_hts_min_max_slope(u_hts_nxcals_dfs, plateau_start, plateau_end, Time.to_unix_timestamp(t_start), slope_range=(-0.5, 0.5))"
339
340
341
342
343
344
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
345
    "## 5.3. DFB Temperature - TT893.TEMPERATURECALC\n",
346
    "\n",
347
348
349
350
351
    "*CRITERIA*:\n",
    "\n",
    "- Check if the temperature is over the dew point, but not overheated -> 280 K < TT893 < 320 K, even without current\n",
    "\n",
    "*GRAPHS*:\n",
352
353
354
    "\n",
    "- Temperature at the top of the current lead on the right axis, TT893.TEMPERATURECALC\n",
    "- Green box denotes the temperature validity region [280, 320] K of the temperature at the top of the current lead\n",
355
    "- t = 0 s corresponds to the start time of the test"
356
357
358
359
   ]
  },
  {
   "cell_type": "code",
360
   "execution_count": null,
361
   "metadata": {
362
363
    "deletable": false,
    "editable": false,
364
365
    "scrolled": false
   },
366
   "outputs": [],
367
   "source": [
368
    "RbCircuitAnalysis.assert_tt893_min_max_value(tt893_nxcals_dfs, value_range=(280, 320))"
369
370
371
372
373
374
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
375
    "## 5.4. DFB Temperature - TT891A.TEMPERATURECALC\n",
376
    "\n",
377
378
379
380
381
    "*CRITERIA*:\n",
    "\n",
    "- Check if the temperature is regulated around 50 K -> 46 K < TT891A < 54 K, even without current\n",
    "\n",
    "*GRAPHS*:\n",
382
383
384
385
    "\n",
    "For odd and even leads\n",
    "- Main power converter current, I_MEAS\n",
    "- Temperature between the HTS and resistive part of the current lead on the right axis, TT891A.TEMPERATURECALC\n",
386
    "- t = 0 s corresponds to the start time of the test\n"
387
388
389
390
   ]
  },
  {
   "cell_type": "code",
391
   "execution_count": null,
392
   "metadata": {
393
394
    "deletable": false,
    "editable": false,
395
396
    "scrolled": false
   },
397
   "outputs": [],
398
   "source": [
399
    "RbCircuitAnalysis.assert_tt891a_min_max_value(tt891a_nxcals_dfs, value_range=(46, 54))"
400
401
402
403
404
405
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
406
    "## 5.5. DFB Valve Regulation - CV891.POSST\n",
407
    "\n",
408
409
410
411
412
413
    "*CRITERIA*:\n",
    "\n",
    "- Check if the valve is opened (>2%), but not fully (<50%)\n",
    "- Check if the valve variation (defined as difference between the maximum and minimum value) does not exceed 8% at constant current (the ramp of the current is excluded this criterion)\n",
    "\n",
    "*GRAPHS*:\n",
414
415
416
417
    "\n",
    "- Main power converter current, I_MEAS\n",
    "- Valve for regulation of TT891A, CV891.POSST\n",
    "- t = 0 s corresponds to the start time of the test\n",
418
    "- Green box denotes the valve opening validity region [2, 50] % of the TT891A temperature regulation"
419
420
421
422
   ]
  },
  {
   "cell_type": "code",
423
   "execution_count": null,
424
   "metadata": {
425
426
    "deletable": false,
    "editable": false,
427
428
    "scrolled": false
   },
429
   "outputs": [],
430
   "source": [
431
    "RbCircuitAnalysis.assert_cv891_min_max_value(cv891_nxcals_dfs, value_range=(2, 50))"
432
433
434
435
   ]
  },
  {
   "cell_type": "code",
436
   "execution_count": null,
437
438
439
440
   "metadata": {
    "deletable": false,
    "editable": false
   },
441
   "outputs": [],
442
   "source": [
443
    "RbCircuitAnalysis.assert_cv891_min_max_variation(cv891_nxcals_dfs, 8, plateau_start, plateau_end, Time.to_unix_timestamp(t_start))"
444
445
446
447
448
449
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
450
    "# 6. Final Report"
451
452
453
454
   ]
  },
  {
   "cell_type": "code",
455
   "execution_count": null,
456
457
458
   "metadata": {
    "editable": false
   },
459
   "outputs": [],
460
461
   "source": [
    "campaign = hwcb.get_campaign()\n",
462
    "apply_report_template()\n",
Michal Maciejewski's avatar
Michal Maciejewski committed
463
    "file_name_html = '{}_{}-{}-{}_report.html'.format(circuit_name, hwc_test, Time.to_datetime(t_start).strftime(\"%Y.%m.%d_%H%M%S\"), analysis_start_time)\n",
464
    "full_path = '/eos/project/l/lhcsm/hwc/RB/{}/{}/{}/{}'.format(circuit_name, hwc_test, campaign, file_name_html)\n",
465
    "!mkdir -p /eos/project/l/lhcsm/hwc/RB/$circuit_name/$hwc_test/$campaign\n",
466
467
468
469
    "print('Compact notebook report saved to (Windows): ' + '\\\\\\\\cernbox-smb' + full_path.replace('/', '\\\\'))\n",
    "display(Javascript('IPython.notebook.save_notebook();'))\n",
    "time.sleep(5)\n",
    "!{sys.executable} -m jupyter nbconvert --to html $'AN_RB_PLI3.a5.ipynb' --output /eos/project/l/lhcsm/hwc/RB/$circuit_name/$hwc_test/$campaign/$file_name_html --TemplateExporter.exclude_input=True --TagRemovePreprocessor.remove_all_outputs_tags='[\"skip_output\"]'"
470
   ]
Michal Maciejewski's avatar
Michal Maciejewski committed
471
472
473
474
475
476
477
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.6.5"
  },
  "sparkconnect": {
   "bundled_options": [
    "SparkMetrics",
    "NXCALS"
   ],
Michal Maciejewski's avatar
Michal Maciejewski committed
503
   "list_of_options": []
504
505
506
507
508
509
510
511
512
513
514
515
516
  },
  "toc": {
   "base_numbering": 1,
   "nav_menu": {},
   "number_sections": false,
   "sideBar": false,
   "skip_h1_title": false,
   "title_cell": "Table of Contents",
   "title_sidebar": "Contents",
   "toc_cell": false,
   "toc_position": {},
   "toc_section_display": true,
   "toc_window_display": false
517
518
519
520
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
Michal Maciejewski's avatar
Michal Maciejewski committed
521
}