Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 17 additions & 35 deletions py-feos/src/eos/epcsaft.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,36 +3,10 @@ use crate::parameter::PyParameters;
use crate::{ideal_gas::IdealGasModel, residual::ResidualModel};
use feos::epcsaft::{ElectrolytePcSaft, ElectrolytePcSaftOptions, ElectrolytePcSaftVariants};
use feos_core::{Components, EquationOfState};
use pyo3::exceptions::PyValueError;
use pyo3::prelude::*;
use std::sync::Arc;

#[derive(Clone, Copy, PartialEq)]
#[pyclass(name = "ElectrolytePcSaftVariants", eq, eq_int)]
pub enum PyElectrolytePcSaftVariants {
Advanced,
Revised,
}

impl From<ElectrolytePcSaftVariants> for PyElectrolytePcSaftVariants {
fn from(value: ElectrolytePcSaftVariants) -> Self {
use ElectrolytePcSaftVariants::*;
match value {
Advanced => Self::Advanced,
Revised => Self::Revised,
}
}
}

impl From<PyElectrolytePcSaftVariants> for ElectrolytePcSaftVariants {
fn from(value: PyElectrolytePcSaftVariants) -> Self {
use PyElectrolytePcSaftVariants::*;
match value {
Advanced => Self::Advanced,
Revised => Self::Revised,
}
}
}

#[pymethods]
impl PyEquationOfState {
/// ePC-SAFT equation of state.
Expand All @@ -45,34 +19,42 @@ impl PyEquationOfState {
/// Maximum packing fraction. Defaults to 0.5.
/// max_iter_cross_assoc : unsigned integer, optional
/// Maximum number of iterations for cross association. Defaults to 50.
/// tol_cross_assoc : float
/// tol_cross_assoc : float, optional
/// Tolerance for convergence of cross association. Defaults to 1e-10.
/// epcsaft_variant : ElectrolytePcSaftVariants, optional
/// Variant of the ePC-SAFT equation of state. Defaults to 'advanced'
/// epcsaft_variant : "advanced" | "revised", optional
/// Variant of the ePC-SAFT equation of state. Defaults to "advanced"
///
/// Returns
/// -------
/// EquationOfState
/// The ePC-SAFT equation of state that can be used to compute thermodynamic
/// states.
#[cfg(feature = "epcsaft")]
#[staticmethod]
#[pyo3(
signature = (parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, epcsaft_variant=PyElectrolytePcSaftVariants::Advanced),
text_signature = "(parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, epcsaft_variant)",
signature = (parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, epcsaft_variant="advanced"),
text_signature = r#"(parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, epcsaft_variant="advanced")"#,
)]
pub fn epcsaft(
parameters: PyParameters,
max_eta: f64,
max_iter_cross_assoc: usize,
tol_cross_assoc: f64,
epcsaft_variant: PyElectrolytePcSaftVariants,
epcsaft_variant: &str,
) -> PyResult<Self> {
let epcsaft_variant = match epcsaft_variant {
"advanced" => ElectrolytePcSaftVariants::Advanced,
"revised" => ElectrolytePcSaftVariants::Revised,
_ => {
return Err(PyErr::new::<PyValueError, _>(
r#"epcsaft_variant must be "advanced" or "revised""#.to_string(),
))
}
};
let options = ElectrolytePcSaftOptions {
max_eta,
max_iter_cross_assoc,
tol_cross_assoc,
epcsaft_variant: epcsaft_variant.into(),
epcsaft_variant,
};
let residual = Arc::new(ResidualModel::ElectrolytePcSaft(
ElectrolytePcSaft::with_options(Arc::new(parameters.try_convert()?), options),
Expand Down
67 changes: 29 additions & 38 deletions py-feos/src/eos/pcsaft.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,36 +8,10 @@ use crate::residual::ResidualModel;
use feos::pcsaft::PcSaftFunctional;
use feos::pcsaft::{DQVariants, PcSaft, PcSaftOptions};
use feos_core::{Components, EquationOfState};
use pyo3::exceptions::PyValueError;
use pyo3::prelude::*;
use std::sync::Arc;

#[derive(Clone, Copy, PartialEq)]
#[pyclass(name = "DQVariants", eq, eq_int)]
pub enum PyDQVariants {
DQ35,
DQ44,
}

impl From<DQVariants> for PyDQVariants {
fn from(value: DQVariants) -> Self {
use DQVariants::*;
match value {
DQ35 => Self::DQ35,
DQ44 => Self::DQ44,
}
}
}

impl From<PyDQVariants> for DQVariants {
fn from(value: PyDQVariants) -> Self {
use PyDQVariants::*;
match value {
DQ35 => Self::DQ35,
DQ44 => Self::DQ44,
}
}
}

#[pymethods]
impl PyEquationOfState {
/// PC-SAFT equation of state.
Expand All @@ -52,32 +26,40 @@ impl PyEquationOfState {
/// Maximum number of iterations for cross association. Defaults to 50.
/// tol_cross_assoc : float, optional
/// Tolerance for convergence of cross association. Defaults to 1e-10.
/// dq_variant : DQVariants, optional
/// Combination rule used in the dipole/quadrupole term. Defaults to 'DQVariants.DQ35'
/// dq_variant : "dq35" | "dq44", optional
/// Combination rule used in the dipole/quadrupole term. Defaults to "dq35"
///
/// Returns
/// -------
/// EquationOfState
/// The PC-SAFT equation of state that can be used to compute thermodynamic
/// states.
#[cfg(feature = "pcsaft")]
#[staticmethod]
#[pyo3(
signature = (parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant=PyDQVariants::DQ35),
text_signature = "(parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant)"
signature = (parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant="dq35"),
text_signature = r#"(parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant="dq35")"#
)]
pub fn pcsaft(
parameters: &Bound<'_, PyAny>,
max_eta: f64,
max_iter_cross_assoc: usize,
tol_cross_assoc: f64,
dq_variant: PyDQVariants,
dq_variant: &str,
) -> PyResult<Self> {
let dq_variant = match dq_variant {
"dq35" => DQVariants::DQ35,
"dq44" => DQVariants::DQ44,
_ => {
return Err(PyErr::new::<PyValueError, _>(
r#"dq_variant must be "dq35" or "dq44""#.to_string(),
))
}
};
let options = PcSaftOptions {
max_eta,
max_iter_cross_assoc,
tol_cross_assoc,
dq_variant: dq_variant.into(),
dq_variant,
};
let parameters = if let Ok(parameters) = parameters.extract::<PyParameters>() {
parameters.try_convert()
Expand Down Expand Up @@ -121,22 +103,31 @@ impl PyHelmholtzEnergyFunctional {
#[cfg(feature = "pcsaft")]
#[staticmethod]
#[pyo3(
signature = (parameters, fmt_version=PyFMTVersion::WhiteBear, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant=PyDQVariants::DQ35),
text_signature = "(parameters, fmt_version, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant)"
signature = (parameters, fmt_version=PyFMTVersion::WhiteBear, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant="dq35"),
text_signature = r#"(parameters, fmt_version, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10, dq_variant="dq35")"#
)]
fn pcsaft(
parameters: crate::parameter::PyParameters,
fmt_version: PyFMTVersion,
max_eta: f64,
max_iter_cross_assoc: usize,
tol_cross_assoc: f64,
dq_variant: PyDQVariants,
dq_variant: &str,
) -> PyResult<PyEquationOfState> {
let dq_variant = match dq_variant {
"dq35" => DQVariants::DQ35,
"dq44" => DQVariants::DQ44,
_ => {
return Err(PyErr::new::<PyValueError, _>(
r#"dq_variant must be "dq35" or "dq44""#.to_string(),
))
}
};
let options = PcSaftOptions {
max_eta,
max_iter_cross_assoc,
tol_cross_assoc,
dq_variant: dq_variant.into(),
dq_variant,
};
let func = Arc::new(ResidualModel::PcSaftFunctional(
PcSaftFunctional::with_options(
Expand Down
2 changes: 0 additions & 2 deletions py-feos/src/eos/pets.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ impl PyEquationOfState {
/// EquationOfState
/// The PeTS equation of state that can be used to compute thermodynamic
/// states.
#[cfg(feature = "pets")]
#[staticmethod]
#[pyo3(signature = (parameters, max_eta=0.5), text_signature = "(parameters, max_eta=0.5)")]
fn pets(parameters: PyParameters, max_eta: f64) -> PyResult<Self> {
Expand Down Expand Up @@ -57,7 +56,6 @@ impl PyHelmholtzEnergyFunctional {
/// Returns
/// -------
/// HelmholtzEnergyFunctional
#[cfg(feature = "pets")]
#[staticmethod]
#[pyo3(
signature = (parameters, fmt_version=PyFMTVersion::WhiteBear, max_eta=0.5),
Expand Down
1 change: 0 additions & 1 deletion py-feos/src/eos/saftvrmie.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ impl PyEquationOfState {
/// EquationOfState
/// The SAFT-VR Mie equation of state that can be used to compute thermodynamic
/// states.
#[cfg(feature = "saftvrmie")]
#[staticmethod]
#[pyo3(
signature = (parameters, max_eta=0.5, max_iter_cross_assoc=50, tol_cross_assoc=1e-10),
Expand Down
2 changes: 0 additions & 2 deletions py-feos/src/eos/saftvrqmie.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@ impl PyEquationOfState {
/// EquationOfState
/// The SAFT-VRQ Mie equation of state that can be used to compute thermodynamic
/// states.
#[cfg(feature = "saftvrqmie")]
#[staticmethod]
#[pyo3(
signature = (parameters, max_eta=0.5, inc_nonadd_term=true),
Expand Down Expand Up @@ -66,7 +65,6 @@ impl PyHelmholtzEnergyFunctional {
/// Returns
/// -------
/// HelmholtzEnergyFunctional
#[cfg(feature = "saftvrqmie")]
#[staticmethod]
#[pyo3(
signature = (parameters, fmt_version=PyFMTVersion::WhiteBear, max_eta=0.5, inc_nonadd_term=true),
Expand Down
58 changes: 17 additions & 41 deletions py-feos/src/eos/uvtheory.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,39 +2,10 @@ use super::PyEquationOfState;
use crate::{ideal_gas::IdealGasModel, parameter::PyParameters, residual::ResidualModel};
use feos::uvtheory::{Perturbation, UVTheory, UVTheoryOptions};
use feos_core::{Components, EquationOfState};
use pyo3::exceptions::PyValueError;
use pyo3::prelude::*;
use std::sync::Arc;

#[derive(Clone, Copy, PartialEq)]
#[pyclass(name = "Perturbation", eq, eq_int)]
pub enum PyPerturbation {
BarkerHenderson,
WeeksChandlerAndersen,
WeeksChandlerAndersenB3,
}

impl From<Perturbation> for PyPerturbation {
fn from(value: Perturbation) -> Self {
use Perturbation::*;
match value {
BarkerHenderson => Self::BarkerHenderson,
WeeksChandlerAndersen => Self::WeeksChandlerAndersen,
WeeksChandlerAndersenB3 => Self::WeeksChandlerAndersenB3,
}
}
}

impl From<PyPerturbation> for Perturbation {
fn from(value: PyPerturbation) -> Self {
use PyPerturbation::*;
match value {
BarkerHenderson => Self::BarkerHenderson,
WeeksChandlerAndersen => Self::WeeksChandlerAndersen,
WeeksChandlerAndersenB3 => Self::WeeksChandlerAndersenB3,
}
}
}

#[pymethods]
impl PyEquationOfState {
/// UV-Theory equation of state.
Expand All @@ -45,28 +16,33 @@ impl PyEquationOfState {
/// The parameters of the UV-theory equation of state to use.
/// max_eta : float, optional
/// Maximum packing fraction. Defaults to 0.5.
/// perturbation : Perturbation, optional
/// Division type of the Mie potential. Defaults to WCA division.
/// perturbation : "BH" | "WCA" | "WCA_B3", optional
/// Division type of the Mie potential. Defaults to "WCA".
///
/// Returns
/// -------
/// EquationOfState
/// The UV-Theory equation of state that can be used to compute thermodynamic
/// states.
#[cfg(feature = "uvtheory")]
#[staticmethod]
#[pyo3(
signature = (parameters, max_eta=0.5, perturbation=PyPerturbation::WeeksChandlerAndersen),
text_signature = "(parameters, max_eta=0.5, perturbation)"
signature = (parameters, max_eta=0.5, perturbation="WCA"),
text_signature = r#"(parameters, max_eta=0.5, perturbation="WCA")"#
)]
fn uvtheory(
parameters: PyParameters,
max_eta: f64,
perturbation: PyPerturbation,
) -> PyResult<Self> {
fn uvtheory(parameters: PyParameters, max_eta: f64, perturbation: &str) -> PyResult<Self> {
let perturbation = match perturbation {
"BH" => Perturbation::BarkerHenderson,
"WCA" => Perturbation::WeeksChandlerAndersen,
"WCA_B3" => Perturbation::WeeksChandlerAndersenB3,
_ => {
return Err(PyErr::new::<PyValueError, _>(
r#"perturbation must be "BH", "WCA" or "WCA_B3""#.to_string(),
))
}
};
let options = UVTheoryOptions {
max_eta,
perturbation: perturbation.into(),
perturbation,
};
let residual = Arc::new(ResidualModel::UVTheory(UVTheory::with_options(
Arc::new(parameters.try_convert()?),
Expand Down