riverine.solver
===============

.. py:module:: riverine.solver

.. autoapi-nested-parse::

   Pure solver functions for mix volume/concentration computation.

   These functions take numeric inputs and return numeric outputs, with no
   dependency on Mix/Action objects. They will be replaced by Rust in Phase 1.



Functions
---------

.. autoapisummary::

   riverine.solver.compute_total_volume
   riverine.solver.compute_fixed_volume_each
   riverine.solver.compute_equal_concentration_each
   riverine.solver.compute_fixed_concentration_each
   riverine.solver.compute_toconcentration_dest_concs
   riverine.solver.compute_fill_volume
   riverine.solver.compute_dest_concentrations
   riverine.solver.validate_mix


Module Contents
---------------

.. py:function:: compute_total_volume(action_effects: Sequence[tuple]) -> riverine.units.DecimalQuantity

   Determine total mix volume from action effects.

   :param action_effects: List of (MixVolumeDep, volume) tuples from each action.
                          MixVolumeDep values: "determines", "independent", "depends".

   :returns: The total volume of the mix.
   :rtype: DecimalQuantity


.. py:function:: compute_fixed_volume_each(fixed_volume: riverine.units.DecimalQuantity, n: int) -> list[riverine.units.DecimalQuantity]

   FixedVolume: each component gets the same fixed volume.

   :param fixed_volume: Volume per component.
   :param n: Number of components.


.. py:function:: compute_equal_concentration_each(fixed_volume: riverine.units.DecimalQuantity, source_concs: list[riverine.units.DecimalQuantity], method: Literal['min_volume', 'max_volume', 'check'] | tuple[Literal['max_fill'], str]) -> list[riverine.units.DecimalQuantity]

   EqualConcentration: adjust volumes so all dest concentrations are equal.

   :param fixed_volume: The reference volume (min or max depending on method).
   :param source_concs: Source concentration of each component.
   :param method: "min_volume", "max_volume", "check", or ("max_fill", buffer_name).


.. py:function:: compute_fixed_concentration_each(mix_vol: riverine.units.DecimalQuantity, fixed_conc: riverine.units.DecimalQuantity, source_concs: list[riverine.units.DecimalQuantity]) -> list[riverine.units.DecimalQuantity]

   FixedConcentration: vol = mix_vol * (fixed_conc / src_conc).

   :param mix_vol: Total mix volume.
   :param fixed_conc: Target destination concentration.
   :param source_concs: Source concentration of each component.


.. py:function:: compute_toconcentration_dest_concs(target_conc: riverine.units.DecimalQuantity, other_concs: list[riverine.units.DecimalQuantity]) -> list[riverine.units.DecimalQuantity]

   ToConcentration: dest = target - already contributed.

   :param target_conc: Target total concentration for each component.
   :param other_concs: Concentration already contributed by other actions, per component.


.. py:function:: compute_fill_volume(target_vol: riverine.units.DecimalQuantity, other_vols_sum: riverine.units.DecimalQuantity) -> riverine.units.DecimalQuantity

   FillToVolume: buffer volume = target - sum(others).

   :param target_vol: Target total volume.
   :param other_vols_sum: Sum of volumes from all other actions.


.. py:function:: compute_dest_concentrations(source_concs: list[riverine.units.DecimalQuantity], each_vols: list[riverine.units.DecimalQuantity], mix_vol: riverine.units.DecimalQuantity) -> list[riverine.units.DecimalQuantity]

   General dest concentration: dest_conc = src_conc * (transfer_vol / mix_vol).

   :param source_concs: Source concentration of each component.
   :param each_vols: Transfer volume of each component.
   :param mix_vol: Total mix volume.


.. py:function:: validate_mix(mixline_names_vols: list[tuple[list[str], riverine.units.DecimalQuantity | None]], total_vol: riverine.units.DecimalQuantity, min_volume: riverine.units.DecimalQuantity, has_fixed_concentration_action: bool, has_fixed_total_volume: bool, buffer_name: str, intermediate_mixes: list[tuple[str, riverine.units.DecimalQuantity, riverine.units.DecimalQuantity]]) -> list[riverine.units.VolumeError]

   All validation checks on a solved mix.

   :param mixline_names_vols: List of (names, total_tx_vol) from each mixline.
   :param total_vol: Total mix volume.
   :param min_volume: Minimum acceptable transfer volume.
   :param has_fixed_concentration_action: Whether any action is FixedConcentration.
   :param has_fixed_total_volume: Whether the mix has a fixed total volume.
   :param buffer_name: Name of the buffer component.
   :param intermediate_mixes: List of (mix_name, mix_fixed_total_vol, needed_vol) for intermediate mix checks.


