mpusz / mp-units

The quantities and units library for C++
https://mpusz.github.io/mp-units/
MIT License
1.07k stars 85 forks source link

value_cast from celsius to kelvin #513

Closed magni-mar closed 11 months ago

magni-mar commented 11 months ago

After reading the documentation it is my understanding that this should be possible, please correct me if I am wrong

#include <iostream>

#include <mp-units/ostream.h>
#include <mp-units/systems/si/units.h>

auto main(int argc, char *argv[]) -> int {

    using namespace mp_units;

    auto q1 = 5 * si::degree_Celsius;
    std::cout << q1.in(si::kelvin) << '\n';

    return EXIT_SUCCESS;
}

this code produces:

5 K

not converting the values but simply changing the type. Is this value_cast possible in some other way?

JohelEGP commented 11 months ago

K and °C are equal in magnitude. If you want different values on conversion, you're probably looking for temperature points. See https://mpusz.github.io/mp-units/2.1/users_guide/framework_basics/the_affine_space/#temperature-support.

mpusz commented 11 months ago

Exactly, as @JohelEGP said. Kelvin and degree Celsius have the same magnitude, so a change of temperature by 5 kelvin equals to the change of 5 degree Celsius.

In case you are interested in temperature points you can check the docs referenced above and also see #506.

mpusz commented 11 months ago

@magni-mar, please let us know if the above addresses your question so we can close this issue.

magni-mar commented 11 months ago

That answered my question, thank you. For future reference for anyone searching this I will include a short sample of this.

#include <iostream>

#include <mp-units/quantity_point.h>
#include <mp-units/systems/si/unit_symbols.h>
#include <mp-units/systems/si/point_origins.h>
#include <mp-units/systems/isq/thermodynamics.h>

auto main(int argc, char *argv[]) -> int {

    using namespace mp_units;

    using kelvin_t = quantity_point<isq::Celsius_temperature[si::unit_symbols::deg_C], si::absolute_zero>;

    constexpr kelvin_t ice_temp =
            si::absolute_zero + 273.15 * isq::Celsius_temperature(1 * si::unit_symbols::deg_C);

    std::cout << "celsius: " << ice_temp.quantity_from(si::ice_point).numerical_value_ << std::endl;
    std::cout << "kelvin: " << ice_temp.quantity_from(si::absolute_zero).numerical_value_ << std::endl;

    using celsius_t = quantity_point<isq::Celsius_temperature[si::unit_symbols::deg_C], si::ice_point>;

    constexpr celsius_t other_temp =
            si::ice_point + 1 * isq::Celsius_temperature(1 * si::unit_symbols::deg_C);

    std::cout << "celsius: " << other_temp.quantity_from(si::ice_point).numerical_value_ << std::endl;
    std::cout << "kelvin: " << other_temp.quantity_from(si::absolute_zero).numerical_value_ << std::endl;

    return 0;
}