Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bug/temp diff #27

Merged
merged 13 commits into from
Aug 8, 2023
46 changes: 41 additions & 5 deletions src/ansys/units/quantity.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
from typing import Tuple

import ansys.units as q
from ansys.units.units import parse_temperature_units


class Quantity(float):
Expand Down Expand Up @@ -83,6 +86,11 @@ def __init__(self, value, units=None, quantity_map=None, dimensions=None):
si_units, si_multiplier, si_offset = self._units_table.si_data(units=self._unit)

self._si_units = si_units

# Well, this is going to have to be a hack, but we
# need to fix the wider design to do this properly
self._fix_temperature_units()

self._si_value = (self.value + si_offset) * si_multiplier

def _arithmetic_precheck(self, __value) -> str:
Expand Down Expand Up @@ -201,7 +209,7 @@ def __mul__(self, __value):
]
new_si_value = self.si_value * __value.si_value
new_dimensions = q.Dimensions(dimensions=temp_dimensions)
new_units = self._temp_precheck() or new_dimensions.units
new_units = new_dimensions.units
return Quantity(value=new_si_value, units=new_units)

if isinstance(__value, (float, int)):
Expand All @@ -218,15 +226,23 @@ def __truediv__(self, __value):
]
new_si_value = self.si_value / __value.si_value
new_dimensions = q.Dimensions(dimensions=temp_dimensions)
new_units = self._temp_precheck() or new_dimensions.units
return Quantity(value=new_si_value, units=new_units)
new_units = new_dimensions.units
result = Quantity(value=new_si_value, units=new_units)
# HACK
convert_to_temp_difference = (
"Temperature" == result.type
and __value.type in ("Temperature", "Temperature Difference")
)
if convert_to_temp_difference:
result._type = "Temperature Difference"
return result

if isinstance(__value, (float, int)):
new_units = self._temp_precheck() or self.si_units
new_units = self.si_units
return Quantity(value=self.si_value / __value, units=new_units)

def __rtruediv__(self, __value):
return self.__truediv__(__value)
return Quantity(__value, "") / self

def __add__(self, __value):
self._arithmetic_precheck(__value)
Expand Down Expand Up @@ -273,6 +289,26 @@ def __neq__(self, __value):
self._arithmetic_precheck(__value)
return float(self) != float(__value)

@staticmethod
def _fix_these_temperature_units(
units: str, ignore_exponent: bool, units_to_search: Tuple[str] = None
) -> str:
new_units = parse_temperature_units(units, ignore_exponent, units_to_search)
return " ".join(
("delta_" + term[0])
if (term[1] and not term[0].startswith("delta_"))
else term[0]
for term in new_units
)

def _fix_temperature_units(self):
# HACK
ignore_exponent = self.type == "Temperature Difference"
self._unit = Quantity._fix_these_temperature_units(self._unit, ignore_exponent)
self._si_units = Quantity._fix_these_temperature_units(
self._si_units, ignore_exponent, ("K",)
)


class QuantityError(ValueError):
"""Custom quantity errors."""
Expand Down
14 changes: 12 additions & 2 deletions src/ansys/units/tables.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import yaml

from ansys.units.quantity import Quantity, QuantityError # noqa: F401
from ansys.units.units import parse_temperature_units


class UnitsTable(object):
Expand Down Expand Up @@ -293,7 +294,16 @@ def get_type(self, units: str) -> str:
if units in self.derived_units:
return "Derived"

if any([temp in units for temp in ["K", "C", "F", "R"]]):
return "Temperature Difference"
# HACK
temperature_units_to_search = ("K", "C", "F", "R")
if any([temp in units for temp in temperature_units_to_search]):
terms = parse_temperature_units(
units,
ignore_exponent=False,
units_to_search=temperature_units_to_search,
)
if any(is_diff for (_, is_diff) in terms):
return "Temperature Difference"
return "Temperature"

return "Composite"
20 changes: 20 additions & 0 deletions src/ansys/units/units.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
from typing import Optional, Tuple


def parse_temperature_units(
units: str, ignore_exponent: bool, units_to_search: Optional[Tuple[str]] = None
) -> list:
if units_to_search is None:
units_to_search = ("K", "C", "F", "R")
units_out = []
for term in units.split(" "):
term_parts = term.split("^")
label = term_parts[0]
exponent = term_parts[0] if len(term_parts) > 1 else "0"
is_temp_diff = (
label
and (exponent != "0" or ignore_exponent)
and label[-1] in units_to_search
)
units_out.append((term, is_temp_diff))
return units_out
62 changes: 46 additions & 16 deletions tests/test_quantity.py
Original file line number Diff line number Diff line change
Expand Up @@ -254,14 +254,14 @@ def test_to_29():
v = q.Quantity(1.0, "BTU lb^-1 R^-1")
to = v.to("J kg^-1 K^-1")
assert to.value == pytest.approx(4186.8161854, DELTA)
assert to.units == "J kg^-1 K^-1"
assert to.units == "J kg^-1 delta_K^-1"
seanpearsonuk marked this conversation as resolved.
Show resolved Hide resolved


def test_to_30():
v = q.Quantity(1.0, "BTU lb^-1 F^-1")
to = v.to("J kg^-1 K^-1")
assert to.value == pytest.approx(4186.8161854, DELTA)
assert to.units == "J kg^-1 K^-1"
assert to.units == "J kg^-1 delta_K^-1"


def test_to_31():
Expand Down Expand Up @@ -537,37 +537,37 @@ def test_temp_7():
hcto1 = hc.to("kJ kg^-1 K^-1")

assert hcto1.value == pytest.approx(1.0, DELTA)
assert hcto1.units == "kJ kg^-1 K^-1"
assert hcto1.units == "kJ kg^-1 delta_K^-1"

hcto2 = hc.to("J kg^-1 C^-1")

assert hcto2.value == pytest.approx(1000.0, DELTA)
assert hcto2.units == "J kg^-1 C^-1"
assert hcto2.units == "J kg^-1 delta_C^-1"

hcto3 = hc.to("kJ kg^-1 C^-1")

assert hcto3.value == pytest.approx(1.0, DELTA)
assert hcto3.units == "kJ kg^-1 C^-1"
assert hcto3.units == "kJ kg^-1 delta_C^-1"

hcto4 = hc.to("cal g^-1 C^-1")

assert hcto4.value == pytest.approx(0.2390057, DELTA)
assert hcto4.units == "cal g^-1 C^-1"
assert hcto4.units == "cal g^-1 delta_C^-1"

hcto5 = hc.to("cal kg^-1 C^-1")

assert hcto5.value == pytest.approx(239.0057, DELTA)
assert hcto5.units == "cal kg^-1 C^-1"
assert hcto5.units == "cal kg^-1 delta_C^-1"

hcto6 = hc.to("kcal kg^-1 C^-1")

assert hcto6.value == pytest.approx(0.2390057, DELTA)
assert hcto6.units == "kcal kg^-1 C^-1"
assert hcto6.units == "kcal kg^-1 delta_C^-1"

hcto7 = hc.to("BTU lb^-1 F^-1")

assert hcto7.value == pytest.approx(0.238845, DELTA)
assert hcto7.units == "BTU lb^-1 F^-1"
assert hcto7.units == "BTU lb^-1 delta_F^-1"


def test_temp_8():
Expand All @@ -576,32 +576,32 @@ def test_temp_8():
temp_varto1 = temp_var.to("g cm^-3 s^-1 K^2")

assert temp_varto1.value == pytest.approx(0.001, DELTA)
assert temp_varto1.units == "g cm^-3 s^-1 K^2"
assert temp_varto1.units == "g cm^-3 s^-1 delta_K^2"

temp_varto2 = temp_var.to("kg mm^-3 s^-1 K^2")

assert temp_varto2.value == pytest.approx(1e-09, DELTA)
assert temp_varto2.units == "kg mm^-3 s^-1 K^2"
assert temp_varto2.units == "kg mm^-3 s^-1 delta_K^2"

temp_varto3 = temp_var.to("kg um^-3 s^-1 K^2")

assert temp_varto3.value == pytest.approx(9.999999999999999e-19, DELTA)
assert temp_varto3.units == "kg um^-3 s^-1 K^2"
assert temp_varto3.units == "kg um^-3 s^-1 delta_K^2"

temp_varto4 = temp_var.to("mg mm^-3 ms^-1 K^2")
temp_varto4 = temp_var.to("mg mm^-3 ms^-1 delta_K^2")

assert temp_varto4.value == pytest.approx(1.0000000000000002e-06, DELTA)
assert temp_varto4.units == "mg mm^-3 ms^-1 K^2"
assert temp_varto4.units == "mg mm^-3 ms^-1 delta_K^2"

temp_varto5 = temp_var.to("g cm^-3 us^-1 K^2")

assert temp_varto5.value == pytest.approx(1e-09, DELTA)
assert temp_varto5.units == "g cm^-3 us^-1 K^2"
assert temp_varto5.units == "g cm^-3 us^-1 delta_K^2"

temp_varto6 = temp_var.to("pg um^-3 ms^-1 K^2")

assert temp_varto6.value == pytest.approx(9.999999999999997e-07, DELTA)
assert temp_varto6.units == "pg um^-3 ms^-1 K^2"
assert temp_varto6.units == "pg um^-3 ms^-1 delta_K^2"


def test_temp_inverse_1():
Expand Down Expand Up @@ -676,6 +676,36 @@ def test_temp_difference():
t = tc1 + td1


def test_temp_diff_combined_multiply():
k = q.Quantity(1.38e-23, "J K^-1")
t = q.Quantity(4.0, "K")
e = k * t
assert e.value == 5.52e-23
assert e.units == "kg m^2 s^-2"


def test_temp_diff_combined_multiply_2():
q1 = q.Quantity(2.0, "J K^-2")
q2 = q.Quantity(4.0, "K")
res = q1 * q2
assert res.value == 8.0
assert res.units == "kg m^2 s^-2 delta_K^-1"


def test_temp_diff_combined_inverse():
t = q.Quantity(4.0, "K")
inv_t = 2.0 / t
assert inv_t.value == 0.5
assert inv_t.units == "delta_K^-1"


def test_temp_diff_combined_divide():
t = q.Quantity(4.0, "K")
t_div = t / 2.0
assert t_div.value == 2.0
assert t_div.units == "K"


def test_core_temp():
t1 = q.Quantity(1.0, "K")
assert float(t1) == 1.0
Expand Down
Loading