Converting between common reference electrodes

[This article was first published on R on chepec, and kindly contributed to R-bloggers]. (You can report issue about the content on this page here)
Want to share your content on R-bloggers? click here if you have a blog, or here if you don't.

A quickly put-together post on the relationships between common electrochemical reference electrode potentials and the vacuum potential, with a proposed algorithm for converting between them.

Reference electrode potentials

Equilibrium potentials at \(\SI{25}{\degreeCelsius}\) for some commonly used reference electrodes. Reproduced from Roberge (2008).

Figure 1: Equilibrium potentials at \(\SI{25}{\degreeCelsius}\) for some commonly used reference electrodes. Reproduced from Roberge (2008).

Graphical comparison of some common reference electrode potential scales. Of course, the scales are going “the wrong way” (we like negative to be up). (Roberge 2008, 67)

Figure 2: Graphical comparison of some common reference electrode potential scales. Of course, the scales are going “the wrong way” (we like negative to be up). (Roberge 2008, 67)

Standard potentials of silver-silver chloride and calomel electrodes at various electrolyte concentrations and temperatures. Reproduced from (Sawyer, Sobkowiak, and Roberts 1995, 192).

Figure 3: Standard potentials of silver-silver chloride and calomel electrodes at various electrolyte concentrations and temperatures. Reproduced from (Sawyer, Sobkowiak, and Roberts 1995, 192).

Standard hydrogen electrode

The SHE contribution to the cell potential is by convention zero at all temperatures. (Inzelt, Lewenstam, and Scholz 2013, 77)

The expression “normal hydrogen electrode” (NHE) is not a synonym for SHE, in fact, the NHE is the historical standard (due to Nernst in 1889) defined as a metal in contact with a solution saturated with hydrogen gas at 1 atm partial pressure and containing \(\SI{1}{\mol\per\cubic\dm}\) sulfuric acid. (Inzelt, Lewenstam, and Scholz 2013, 77) The NHE is thus experimentally realisable.

In contrast, the SHE is an ideal device and cannot be rigorously realised experimentally. For practical realisation the standard potential of the hydrogen electrode is not measured at standard conditions but recalculated to \(\ce{H+}\) at unit activity and \(\SI{10E5}{\pascal}\). These electrodes are often called reversible hydrogen electrodes (RHE).

Inzelt, Lewenstam, and Scholz (2013), p. 78

Calomel electrode

  • Decimolar (decinormal) calomel electrode, \(c_\ce{KCl}=\SI{0.1}{\mol\per\litre}\), \(E = \SI{0.3337}{\volt}\).
  • Molar (normal) calomel electrode, \(c_\ce{KCl}=\SI{1}{\mol\per\litre}\), \(E = \SI{0.2801}{\volt}\).
  • Saturated calomel electrode (SCE), \(c_\ce{KCl}\approx\SI{4.2}{\mol\per\litre}\), \(E = \SI{0.2412}{\volt}\).

All potential values above at \(\SI{25}{\degreeCelsius}\) and taken from Bagotsky (2006), p. 194. Because of solubility changes, SCE has a large temperature coefficient (\(\SI{0.65}{\mV\per\kelvin}\)). The potentials of calomel electrodes can be reproduced to \(\SI{+-0.1}{\mV}\).

Calomel electrodes are unstable much above \(\SI{50}{\degreeCelsius}\) owing to the disproportionation reaction \(\ce{Hg2Cl2 -> Hg(liq) + HgCl2}\). (eDAQ wiki)

Marcus (1980) reports \(E^\circ_{\ce{Hg/Hg2Cl2}} = \SI{0.26818+-0.00002}{\volt}\) at \(\SI{298.15}{\kelvin}\) (\(a_{\ce{Cl^-}} = 1\)).

Silver-silver chloride electrode

\(E^0 = \SI{0.2224}{\volt}\) at \(\SI{25}{\degreeCelsius}\) (\(a_{\ce{Cl-}}=1\)). (Bagotsky 2006, 195; Inzelt, Lewenstam, and Scholz 2013, 87)

The standard potential of the Ag/AgCl electrode has been reported at temperatures exceeding \(\SI{100}{\degreeCelsius}\).

The absolute potential scale

Conversion of relative reference electrode potentials into electronic energies for aqueous systems. Reproduced from Trasatti (1986).

Figure 4: Conversion of relative reference electrode potentials into electronic energies for aqueous systems. Reproduced from Trasatti (1986).

Trasatti (1986) shows a calculation of the absolute potential of SHE in water and recommends the following conversion:

\[\begin{equation} E^\circ(\ce{H+}/\ce{H2})^{\ce{H2O}}\text{(abs)} = \SI{4.44+-0.02}{\volt}\quad\mathrm{at}~\SI{298.15}{\kelvin} \end{equation}\]

It is to be noted that the uncertainty in the knowledge of \(E^\circ(\ce{H+}/\ce{H2})\text{(abs)}\) (\(\SI{+-20}{\mV}\)) by far exceeds the accuracy of most measurements of electrode potentials. Therefore, any convenience in the use of the absolute potential scale is confined to the specific cases when calculations of electronic energy levels are needed.

Trasatti (1986)

On this topic there is also an interesting discussion in Morrison (1980), p. 31.

I did a quick scan of all papers that cite Trasatti (1986), and found no more recent recommendation on the relation between SHE and AVS. For now we will stick with Trasatti’s value.

The precise relation between the potential of a free electron in vacuum (absolute vacuum scale) and the conventional standard hydrogen electrode scale for aqueous solutions is still debated. (Inzelt, Lewenstam, and Scholz 2013)

Notes

[…] mercury-containing REs (calomel or mercury–mercuric oxide) are inappropriate for measurements in conjunction with platinum electrodes, since the mercury ions readily poison platinum surfaces.

(Bagotsky 2006, 195)

If this is a rule, we break it quite often.

Convert to or from any* electrode scale

Note: this section was updated on Oct 18th, 2019 because I moved the reference electrode functions into their own R package refelectrodes.

Having the the conversion algorithm in its own package like this should make the codebase easier to maintain and improve going forward. If you have any suggestions or comments regarding the data or the code of this package please don’t hesitate to open an issue or pull request on Github. I would be very grateful to hear any feedback.

* Any here denotes any one of the reference electrode scales that the refelectrodes package currently supports:

  • AgCl/Ag in saturated NaCl(aq) at RT, in saturated KCl(aq) from \(\SIrange{10}{40}{\degreeCelsius}\), and in \(\SI{3.5}{\mol\per\litre}\) KCl(aq) from \(\SIrange{10}{40}{\celsius}\),
  • Hg2Cl2/Hg in saturated KCl(aq) from \(\SIrange{10}{40}{\celsius}\), in \(\SI{3.5}{\mol\per\litre}\) KCl(aq) from \(\SIrange{10}{40}{\celsius}\), in \(\SI{1.0}{\mol\per\litre}\) KCl(aq) from \(\SIrange{10}{40}{\celsius}\), and in \(\SI{0.1}{\mol\per\litre}\) KCl(aq) from \(\SIrange{10}{40}{\celsius}\),
  • SHE (it is zero at all temperatures and concentrations by definition),
  • Li at RT,
  • Na at RT,
  • Mg at RT, and
  • the absolute vacuum scale at RT.

This data is defined in the potentials.as.SHE() function which constitutes the core of the refelectrodes package.

As for the conversion functions, those are the aptly named as.SHE() which converts from any reference electrode scale to SHE, and from.SHE() which converts from SHE to any of the other scales.

The package also exports RefCanonicalName() which is a convenience function that allows the user to specify the name of each reference electrode scale using any of its common names. And that is effectively the extent of the package.1

Let’s take a quick walk through loading this package and testing its functions. You will want to start by installing and loading the package:

remotes::install_github("chepec/refelectrodes")
library(refelectrodes)
# I suggest you load these packages if you want to replicate the plot below
library(knitr)
library(ggplot2)
library(ggrepel)
library(dplyr)
library(magrittr)

The core function defines the dataset and when run will happily return this data as a tidy dataframe (this chunk shows just an excerpt of the tibble):

potentials.as.SHE() %>%
   group_by(electrode, electrolyte) %>%
   arrange(SHE) %>%
   # return first and last row (if any) within each group
   filter(row_number() %in% c(1, n())) %>%
   arrange(electrode, SHE)
## # A tibble: 11 x 9
## # Groups:   electrode, electrolyte [8]
##    electrode electrolyte conc.num conc.string   temp    SHE sid   reference     dEdT
##    <chr>     <chr>          <dbl> <chr>        <dbl>  <dbl> <chr> <chr>        <dbl>
##  1 AgCl/Ag   "KCl(aq)"        4.2 "saturated"    40   0.184 2     Sawyer19… -1.00e-3
##  2 AgCl/Ag   "KCl(aq)"        3.5 "3.5M at 25…   10   0.215 1     Sawyer19… -7.36e-4
##  3 AgCl/Ag   "NaCl(aq)"       5.9 "saturated"    25   0.263 9     CRC 97th… NA      
##  4 AVS       ""              NA   ""             25  -4.44  7     Trasatti… NA      
##  5 Hg2Cl2/Hg "KCl(aq)"        4.2 "saturated"    40   0.234 6     Sawyer19… -6.64e-4
##  6 Hg2Cl2/Hg "KCl(aq)"        0.1 "0.1M at 25…   25   0.336 3     Sawyer19… -7.86e-5
##  7 Li        ""               1   "1.0M at 25…   25  -3.04  10    CRC 97th… NA      
##  8 Mg        ""               1   "1.0M at 25…   25  -2.37  12    CRC 97th… NA      
##  9 Na        ""               1   "1.0M at 25…   25  -2.71  11    CRC 97th… NA      
## 10 SHE       ""              NA   ""           -273.  0     8     Inzelt20…  0.     
## 11 SHE       ""              NA   ""            580   0     8     Inzelt20…  0.

The dataframe is tidy, so more data can easily be added to this dataset by adding more rows.

Now, some of the the columns of this dataframe warrant some explanation. potentials$electrode is the name of the reference electrode, as defined by the function RefCanonicalName() (see below). potentials$conc.string was added so that the user does not need to remember the saturation concentration for various salts in solution. And for those unsaturated electrolytes it was a good place to put information on the temperature where the concentration was defined. Saturation does not depend on temperature, but the concentration of an unsaturated solution (expressed as amount/volume) does depend on temperature due to liquid expansion. Temperature and concentration values need no further explanation. potentials$setid is mainly for housekeeping – a simple way to keep track of the datasets in the dataframe (allows us to avoid having to resort to advanced matching against several parameters to later identify a particular set).

Note that no conversion happens in the potentials.as.SHE() function above. It just returns data.

Conversion is handled by the two functions as.SHE() and from.SHE(). The take the following arguments: the potential value (in volt), the scale (for the scale you want to convert from in the case of as.SHE(), and the one you want to convert to in the case of from.SHE()), and optional arguments for concentration and temperature (set to saturated and RT by default). The last argument expects the dataframe generated by potentials.as.SHE.

This way, all three of these functions are reasonably modular, and each one does a fairly well-defined job.

Some special considerations which are handled by these functions are perhaps worth mentioning here:

  • concentration may be a number or a character string, which means we need to compare it to the appropriate column in the dataset,
  • the temperature requested by the user may coincide with a datapoint in the dataset (in that case we just return that potential), otherwise we interpolate (by linear regression) based on the existing data,
  • and for the final calculation of potential in SHE scale, we need to handle electronic (vacuum) and electrochemical scales separately because they go in opposite directions (this is handled by the ifelse(df$vacuum[p], ...) call.

The current implementation requires concentration to match an existing value. A functionality that could (perhaps even should) be added is the ability to interpolate concentrations in the same way as temperature (unless the change in potential with changing concentration deviates strongly from linearity).

Plotting the dataset

ggplot(potentials.as.SHE() %>%
          filter(electrolyte == "KCl(aq)")) +
   facet_wrap(~ electrode, ncol = 2) +
   geom_line(aes(x = temp, y = SHE, colour = conc.string)) +
   geom_point(aes(x = temp, y = SHE, colour =  conc.string)) +
   geom_text_repel(data = subset(potentials.as.SHE(), electrode != "AVS" & temp == 30),
                   aes(y = SHE, x = temp, label = conc.string, colour = conc.string),
                   point.padding = unit(0.25, 'lines'),
                   # hide the line connecting datapoint and label
                   segment.color = "transparent") +
   scale_y_reverse() +
   labs(x = expression("T/"*degree*C), # "T/C",
        y = "E/V vs SHE") +
   theme(legend.position = "none")
Electrode potentials vs SHE for the two reference electrodes in the dataset using \(\ce{KCl(aq)}\) electrolyte (each panel shows one reference electrode, each line shows a different electrolyte concentration). Just to demonstrate the extent of the dataset in parameter space.

Figure 5: Electrode potentials vs SHE for the two reference electrodes in the dataset using \(\ce{KCl(aq)}\) electrolyte (each panel shows one reference electrode, each line shows a different electrolyte concentration). Just to demonstrate the extent of the dataset in parameter space.

A very simple interactive demo

Open the Shiny demo on its own page

SessionInfo

## R version 3.6.2 (2019-12-12)
## Platform: x86_64-pc-linux-gnu (64-bit)
## Running under: Ubuntu 18.04.4 LTS
## 
## Matrix products: default
## BLAS:   /usr/lib/x86_64-linux-gnu/blas/libblas.so.3.7.1
## LAPACK: /usr/lib/x86_64-linux-gnu/lapack/liblapack.so.3.7.1
## 
## locale:
##  [1] LC_CTYPE=en_GB.UTF-8       LC_NUMERIC=C              
##  [3] LC_TIME=en_GB.UTF-8        LC_COLLATE=en_GB.UTF-8    
##  [5] LC_MONETARY=en_GB.UTF-8    LC_MESSAGES=en_GB.UTF-8   
##  [7] LC_PAPER=en_GB.UTF-8       LC_NAME=C                 
##  [9] LC_ADDRESS=C               LC_TELEPHONE=C            
## [11] LC_MEASUREMENT=en_GB.UTF-8 LC_IDENTIFICATION=C       
## 
## attached base packages:
## [1] stats     graphics  grDevices utils     datasets  methods   base     
## 
## other attached packages:
## [1] refelectrodes_0.0.0.9000 common_0.0.1.9000        magrittr_1.5            
## [4] dplyr_1.0.0              ggrepel_0.8.2            ggplot2_3.3.2           
## [7] knitr_1.29              
## 
## loaded via a namespace (and not attached):
##  [1] Rcpp_1.0.4.6     tidyselect_1.1.0 munsell_0.5.0    colorspace_1.4-1
##  [5] R6_2.4.1         rlang_0.4.6      stringr_1.4.0    tools_3.6.2     
##  [9] grid_3.6.2       gtable_0.3.0     xfun_0.15        withr_2.2.0     
## [13] htmltools_0.5.0  ellipsis_0.3.1   yaml_2.2.1       digest_0.6.25   
## [17] tibble_3.0.1     lifecycle_0.2.0  crayon_1.3.4     bookdown_0.20   
## [21] purrr_0.3.4      vctrs_0.3.1      glue_1.4.1       evaluate_0.14   
## [25] rmarkdown_2.3    blogdown_0.20    stringi_1.4.6    compiler_3.6.2  
## [29] pillar_1.4.4     generics_0.0.2   scales_1.1.1     pkgconfig_2.0.3

References

Bagotsky, V. S. 2006. Fundamentals of Electrochemistry. 2nd ed. Wiley-Interscience.

Inzelt, György, Andrzej Lewenstam, and Fritz Scholz, eds. 2013. Handbook of Reference Electrodes. Berlin, Heidelberg: Springer Berlin Heidelberg. https://doi.org/10.1007/978-3-642-36188-3.

Marcus, Y. 1980. “Compilation and Evaluation of Solubility Data in the Mercury (I) Chloride-Water System.” Journal of Physical and Chemical Reference Data 9 (4): 1307. https://doi.org/10.1063/1.555633.

Morrison, S. Roy. 1980. Electrochemistry at Semiconductor and Oxidized Metal Electrodes. 1st ed. Plenum press.

Roberge, Pierre R. 2008. Corrosion Engineering Principles and Practice. https://doi.org/10.1036/0071482431.

Sawyer, Donald T., Andrzej Sobkowiak, and Julian L. Roberts. 1995. Electrochemistry for Chemists. Second. John Wiley & Sons, Inc.

Trasatti, S. 1986. “The Absolute Electrode Potential: An Explanatory Note (Recommendations 1986).” Pure and Applied Chemistry 58 (7): 955–66. https://doi.org/10.1351/pac198658070955.


  1. The package also contains a slew of deprecated functions that are clearly marked as such and may be removed in a future update.↩︎

To leave a comment for the author, please follow the link and comment on their blog: R on chepec.

R-bloggers.com offers daily e-mail updates about R news and tutorials about learning R and many other topics. Click here if you're looking to post or find an R/data-science job.
Want to share your content on R-bloggers? click here if you have a blog, or here if you don't.

Never miss an update!
Subscribe to R-bloggers to receive
e-mails with the latest R posts.
(You will not see this message again.)

Click here to close (This popup will not appear again)