# ChemCal

<!-- WARNING: THIS FILE WAS AUTOGENERATED! DO NOT EDIT! -->

## Install

``` sh
pip install ChemCal
```

## How to use

First we generate some data to work with.

``` python
# generate training data and sample data
test_data = pd.DataFrame({'concentration': [0.2, 0.05, 0.1, 0.8, 0.6, 0.4], "abs": [0.221, 0.057, 0.119, 0.73, 0.599, 0.383]})
sample_data = pd.DataFrame({'unknown': [0.490, 0.471, 0.484, 0.473, 0.479, 0.492]})
```

Now, create a CalibrationModel object and pass the predictor and
response variables from our dataset as the x and y values respectively.

``` python
cal = CalibrationModel(x=test_data['concentration'], y=test_data['abs'])
```

When we call .fit_ols(), an ordinary least squares regression is fit to
the data and the slope, intercept and values are stored in the object
and can be retrieved by calling `.slope`, `.intercept` and `.r_squared`
respectively.

``` python
cal.fit_ols()

print(f"Slope: {cal.slope: .3f}" )
print(f"Intercept: {cal.intercept: .3f}" )
print(f"R2: {cal.r_squared: .3f}" )
```

    Slope:  0.904
    Intercept:  0.027
    R2:  0.998

We can also call the method `.linest_stats()` to return a series of
statistics you might expect when using the linest function in excel or
sheets.

``` python
cal.linest_stats()
```

<div>
<style scoped>
    .dataframe tbody tr th:only-of-type {
        vertical-align: middle;
    }
&#10;    .dataframe tbody tr th {
        vertical-align: top;
    }
&#10;    .dataframe thead th {
        text-align: right;
    }
</style>

|     | Slope    | Intercept | Uncertainty in slope | Uncertainty in intercept | Standard error of regression | F-statistic | Degrees of freedom | Regression sum of squares | Residual sum of squares |
|-----|----------|-----------|----------------------|--------------------------|------------------------------|-------------|--------------------|---------------------------|-------------------------|
| 0   | 0.904411 | 0.027419  | 0.0312               | 0.017178                 | 0.020745                     | 840.261133  | 4                  | 0.361606                  | 0.001721                |

</div>

Finally, we can calculate an inverse prediction from unknown data and
retrieve the uncertainty but calling .inverse_prediction().

``` python
pred = cal.inverse_prediction(sample_data['unknown'])
print(pred)
```

    0.5020733029033536 ± 0.031053583676141718

The uncertainty is calculated according to the following expression:

$$ U = {S_{\\hat{x}}}_0 * T $$

Where if a single sample is provided:

$$ {S_{\hat{x}}}_0 = \frac{S_{y/x}}{b} \sqrt{\frac{1}{m} + \frac{1}{n}} $$

Or, if multiple replicate samples are provided:

$$ s_{\hat{x}_0}=\frac{1}{b} \sqrt{\frac{s_r^2}{m}+\frac{s_{y / x}^2}{n}+\frac{s_{y / x}^2\left(y_0-\bar{y}\right)^2}{b^2 \sum_{i=1}^n\left(x_i-\bar{x}\right)^2}} $$
