Skip to content

Instantly share code, notes, and snippets.

@erikyo
Created May 8, 2018 20:25
Show Gist options
  • Star 5 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save erikyo/3baa42d4d1f07e93913eaedb76fe64dc to your computer and use it in GitHub Desktop.
Save erikyo/3baa42d4d1f07e93913eaedb76fe64dc to your computer and use it in GitHub Desktop.
Max Dissolved Oxigen Saturation over a range of user-specified values for water temperature, barometric pressure, and salinity or specific conductance.
// --------- Max Dissolved Oxigen Saturation ------------//
//
// Equation for the Henry coefficient as a function of temperature and salinity is used to calculate values
// for unit standard atmospheric concentrations (USAC) in freshwater and seawater in equilibrium with air at a total pressure
// of 1 atmosphere. It is estimated that the possible error in the new USAC values is no greater than $\pm 0.1%$ and probably less.
// Tables and equations are presented for obtaining accurate USAC values in the ranges $0^\circ < t < 40^\cir C and 0 < S < 40$.
// Simple procedures are given for calculating standard atmospheric concentrations at pressures different from 1 atm.
//
// Reference https://water.usgs.gov/software/DOTABLES/
// Dissolved oxygen (DO) solubility over a range of user-specified values for
// water temperature, barometric pressure, and salinity or specific conductance.
// Low memory usage function for Arduino, esp 8266 who can estimate the DO,
// useful for water testing, hydroponics and aquarium automation etc
// Functions
float getMaxDO(float wt, float pres = NULL, int ppm = NULL) {
float sat,tk, bp, sal, sc;
// compute Kelvin temperature
tk = wt + 273.15;
// compute oxygen solubility in freshwater at 1 atm and input temperature
sat = exp(-139.34411 +(1.575701E5 +(-6.642308E7 +(1.2438E10 -8.621949E11/tk)/tk)/tk)/tk);
// if have pressure data
if (pres) {
// convert bp to atmospheres
bp /= 1013.25;
// compute pressure correction
float u, theta;
u = exp(11.8571 +(-3840.70 -216961/tk)/tk);
theta = 0.000975 -1.426E-5 * wt +6.436E-8 * wt * wt;
sat *= (bp - u)*(1 - theta * bp)/((1 - u)*(1 - theta));
}
// if ec
if (ppm) {
// will use the original dotable variable name
sc = ppm;
// convert ppm to salinity
sal = 5.572E-4 * sc + 2.02E-9 * sc * sc;
// compute salinity correction
sat *= exp(-1 * sal * (0.017674 +(-10.754 +2140.7/tk)/tk));
}
return sat;
}
void setup() {
}
void loop() {
// your vars
float my_wt = 25.00;
float my_pres = 1010.00; // input pressure expressed in millibars
int my_ppm = 1000; // input your TDS PPM
float MaxDO; // our return var
MaxDO = getMaxDO(my_wt, my_pres, my_ppm);
Serial.print("Max Dissolved oxygen (DO) solubility of ");
Serial.print(MaxDO);
Serial.print("mg/L at ");
Serial.print(my_wt);
Serial.print("°");
if (my_pres) {
Serial.print(" with ");
Serial.print(my_pres);
Serial.print("millibars");
}
if (my_ppm) {
Serial.print(" and at ");
Serial.print(my_ppm);
Serial.print(" TDS PPM");
}
Serial.println();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment