<SYSTEM_TASK:>
Given the following text description, write Python code to implement the functionality described below step by step
<END_TASK>
<USER_TASK:>
Description:
 Notebook for cellpy batch processing
You can fill inn the MarkDown cells (the cells without "numbering") by double-clicking them. Also remember, press shift + enter to execute a cell.
A couple of useful links
Step1:  Creating pages and initialise the cellpy batch object
If you need to create Journal Pages, please provide appropriate names for the project and the experiment to allow cellpy to build the pages.
Step2:  Initialisation
Step3:  Set parameters
Step4:  Run
Step5:  4. Looking at the data
Step6:  Using hvplot for plotting summaries
Step7:  Looking closer at some summary-plots
Step8:  5. Checking for more details per cycle
A. pick the CellpyData object for one of the cells
Step9:  B. Get some voltage curves for some cycles and plot them
The method get_cap can be used to extract voltage curves.
Step10:  Looking at some dqdv data
Get capacity cycles and make dqdv using the ica module
Step11:  Put it in a for-loop for plotting many ica plots
Step12:  Get all the dqdv data in one go
<ASSISTANT_TASK:>
Python Code:
import numpy as np
import matplotlib.pyplot as plt
import cellpy
from cellpy import prms
from cellpy import prmreader
from cellpy.utils import batch
%matplotlib inline
## Uncomment this and run for checking your cellpy parameters.
# prmreader.info()
Explanation: Notebook for cellpy batch processing
You can fill inn the MarkDown cells (the cells without "numbering") by double-clicking them. Also remember, press shift + enter to execute a cell.
A couple of useful links:
 - How to write MarkDown
 - Jupyter notebooks
 - cellpy
This notebook uses the following packages
python >= 3.6 
cellpy >= 0.3.3
pandas
numpy
matplotlib
bokeh
pyviz (holoviews)
0. Setting up things properly
0.1 Installing cellpy
For this to work, you will have to have a version of cellpy satisfying the criteria in the paragraph above. You might have to do a pre-release install to get it or clone the github repository and install in developer-mode.
Installing a pre-release with pip.
bash
pip install --upgrade --pre cellpy
(if this is the first time you install cellpy, you can skip the --upgrade option)
Installing after cloning using pip in developer-mode. Note that you have to be in the directory where you have put the cellpy package (where the setup.py file is), if not, using . as argument will not work and you will have to provide the full path to the setup.py file):
bash
pip install -e .
0.2 Make sure you have a properly working config file
For cellpy to find stuff, it needs to know where to look. A config file exists for this purpose. It is typically located in your home directory (for mac and linux) or in your documents directory (for Windows) and has a name on this form (replacing "username" with your real username):
.cellpy_prms_username.conf
The file format is YAML (be aware that it cares about white spaces). The most important settings for this notebook are probably the Paths. Make sure they make sense (and that both the paths and the db_path filename exist) and edit it if necessary.
Here is how a typical file (at least the top of it) looks like:
```yaml
Paths:
  cellpydatadir: cellpy_data/cellpyfiles
  db_filename: cellpy_db.xlsx
  db_path: cellpy_data/db
  filelogdir: cellpy_data/logs
  outdatadir: cellpy_data/out
  rawdatadir: cellpy_data/raw
  examplesdir: cellpy_data/examples
  notebookdir: cellpy_data/notebooks
  batchfiledir: cellpy_data/batchfiles
FileNames:
  file_name_format: YYYYMMDD_[NAME]EEE_CC_TT_RR
Db:
  db_type: simple_excel_reader
  db_table_name: db_table
  db_header_row: 0
  db_unit_row: 1
  db_data_start_row: 2
  ...
```
0.3 Database file
This notebook uses the cellpy batch utility. For it to work properly (or at all) you will have to provide it with a database. You can choose to implement a database and a loader your self. Currently, cellpy ships with a very simple database solution that hardly justifies its name as a database. It reads an excel-file where the first row acts as column headers, the second provides the type (e.g. string, bool, etc), and the rest provides the necessary information for each of the cells (one row pr. cell).
A sample excel file ("db-file") is provided with this example. You will need fill inn values manually, one row for each cell you want to load. Then you will have to put it in the database folder (as defined in your config file where it says db_file: in the Paths-section). The name of the file must also be the same as defined in the config-file (db_filename:, i.e cellpy_db.xlsx in the example config file snippet above).
When cellpy reads the file, it uses the batch column (see below) to select which rows (i.e. cells) to load. For example, if the "b01" batch column is the one you tell cellpy to use and you provide it with the name "casandras_experiment", it will only select the rows that has "casandras_experiment" in the "b01" column. You provide cellpy with the "lookup" name when you issue the batch.init command, for example:
python
b = batch.init("casandras_experiment", "cool_project", batch_col="b01")
You must always have the columns colored green filled out. And make sure that the id column (the first one in the example xlsx file) has a unique integer for each row (it is used as a "key" when looking up stuff from the file).
0.4 Files to read
Make sure that the names of your experiment-files (for example your .res files) are on the form date_something_that_describes_the_cell.res because this is the name-format supported at the moment (this is not strictly true, but just to be on the safe side...).
OK, thats all for now. Have a look at the source code in the github repository or 
1. Key information about the current experiment
Experimental-id: xxx
Short-name: xxx
Project: project name
By: your name
Date: xx.xx.xxxx
2. Short summary of the experiment before processing
It is often helpful to formulate what you wanted to achieve with your experiment before actually going into depth of the data. I believe that it does not make you "biased" when processing your data, but instead sharpens your mind and motivates you to look more closely on your results. I might be wrong, off course. Then just skip filling in this part.
Main purpose
(State the main hypothesis for the current set of experiment)
Expected outcome
(What do you expect to find out? What kind of tests did you perform?)
Special considerations
(State if there are any special considerations for this experiment)
3. Processing data
Setting up everything
End of explanation
# Please fill in here
project = "xxx"
name = "xxx"
batch_col = "b01"
Explanation: Creating pages and initialise the cellpy batch object
If you need to create Journal Pages, please provide appropriate names for the project and the experiment to allow cellpy to build the pages.
End of explanation
print(" INITIALISATION OF BATCH ".center(80, "="))
b = batch.init(name, project, batch_col=batch_col)
Explanation: Initialisation
End of explanation
# setting some prms
b.experiment.export_raw = False
# b.experiment.export_cycles = True
# b.experiment.export_ica = True
Explanation: Set parameters
End of explanation
# load info from your db and write the journal pages
b.create_journal()
# create the apropriate folders
b.paginate()
# load the data (and save .csv-files if you have set export_(raw/cycles/ica) = True)
# (this might take some time)
b.update()
# collect summary-data (e.g. charge capacity vs cycle number) from each cell and export to .csv-file(s).
b.combine_summaries()
Explanation: Run
End of explanation
# Plot the charge capacity and the C.E. (and resistance) vs. cycle number (standard plot)
b.plot_summaries()
# Show the journal pages
b.pages
Explanation: 4. Looking at the data
End of explanation
import hvplot.pandas
import holoviews as hv
# hvplot does not like infinities
s = b.summaries.replace([np.inf, -np.inf], np.nan)
layout = (
    s["coulombic_efficiency"].hvplot()
    + s["discharge_capacity"].hvplot() * s["charge_capacity"].hvplot()
)
layout.cols(1)
s["cumulated_coulombic_efficiency"].hvplot()
Explanation: Using hvplot for plotting summaries
End of explanation
discharge_capacity = b.summaries.discharge_capacity
charge_capacity = b.summaries.charge_capacity
coulombic_efficiency = b.summaries.coulombic_efficiency
ir_charge = b.summaries.ir_charge
fig, (ax1, ax2) = plt.subplots(2, 1)
ax1.plot(discharge_capacity)
ax1.set_ylabel("capacity ")
ax2.plot(ir_charge)
ax2.set_xlabel("cycle")
ax2.set_ylabel("resistance")
Explanation: Looking closer at some summary-plots
End of explanation
# Lets check what cells we have
cell_labels = b.experiment.cell_names
cell_labels
# OK, then I choose one of them
label = cell_labels[0]
data = b.experiment.data[label]
Explanation: 5. Checking for more details per cycle
A. pick the CellpyData object for one of the cells
End of explanation
cap = data.get_cap(categorical_column=True)
cap.head()
fig, ax = plt.subplots()
ax.plot(cap.capacity, cap.voltage)
ax.set_xlabel("capacity")
ax.set_ylabel("voltage")
c4, v4 = data.get_cap(cycle=4, method="forth-and-forth")
c10, v10 = data.get_cap(cycle=10, method="forth-and-forth")
fig, ax = plt.subplots()
ax.set_xlabel("capacity")
ax.set_ylabel("voltage")
ax.plot(c4, v4, "ro", label="cycle 4")
ax.plot(c10, v10, "bs", label="cycle 22")
ax.legend();
Explanation: B. Get some voltage curves for some cycles and plot them
The method get_cap can be used to extract voltage curves.
End of explanation
from cellpy.utils import ica
v4, dqdv4 = ica.dqdv_cycle(
    data.get_cap(4, categorical_column=True, method="forth-and-forth")
)
v10, dqdv10 = ica.dqdv_cycle(
    data.get_cap(10, categorical_column=True, method="forth-and-forth")
)
plt.plot(v4, dqdv4, label="cycle 4")
plt.plot(v10, dqdv10, label="cycle 10")
plt.legend();
Explanation: Looking at some dqdv data
Get capacity cycles and make dqdv using the ica module
End of explanation
fig, ax = plt.subplots()
for cycle in data.get_cycle_numbers():
    d = data.get_cap(cycle, categorical_column=True, method="forth-and-forth")
    if not d.empty:
        v, dqdv = ica.dqdv_cycle(d)
        ax.plot(v, dqdv)
    else:
        print(f"cycle {cycle} seems to be missing or corrupted")
Explanation: Put it in a for-loop for plotting many ica plots
End of explanation
hv.extension("bokeh")
tidy_ica = ica.dqdv_frames(data)
cycles = list(range(1, 3)) + [10, 15]
tidy_ica = tidy_ica.loc[tidy_ica.cycle.isin(cycles), :]
%%opts Curve [xlim=(0,1)] NdOverlay [legend_position='right']
#legend_cols=True]
curve4 = (hv.Curve(tidy_ica, kdims=['voltage'], vdims=['dq', 'cycle'], label="Incremental capacity plot")
          .groupby("cycle")
          .opts(
              style={"Curve": dict(color=hv.Palette("Viridis"))},
          )
          .overlay()
          .opts(
              width=800,
              height=500,
          )
         )
curve4
Explanation: Get all the dqdv data in one go
End of explanation
<END_TASK>