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

Integrate with astropy units? #26

Open
sjchilcote opened this issue Mar 25, 2019 · 2 comments
Open

Integrate with astropy units? #26

sjchilcote opened this issue Mar 25, 2019 · 2 comments

Comments

@sjchilcote
Copy link

sjchilcote commented Mar 25, 2019

This library is wonderful, but it'd be really handy if it were possible to replace the element properties with Quantities from Astropy's unit system if Astropy is installed (and the user explicitly requests it, probably.)

This would enable the user to do things like

    >>> 100 * cm**3 * Au.density
    <Quantity 1930. cm3 g / cm3>
    >>> _.to(kg)
    <Quantity 1.93 kg>

Currently I have to do periodictable.Au.density * u.Unit(periodictable.Au.density_units) every time I use a value from the table.

Might see a PR from me in a few weeks, unless you think this is a bad idea.

@pkienzle
Copy link
Collaborator

(1) How to do this without changing interfaces and breaking existing code?

(2) How to do this without using a particular unit system? I'm sure astropy.units is fine, but I suspect there are other units systems out there that are equally good. For example, units, quantities, Unum, ScientificPython (Scientific.Physics.PhysicalQuantity), sympy (sympy.physics.units), simtk.unit, python-units, ...

(3) How to do this so that only systems that want it have to pay for it? It would be nice if python had proper macros so that units could be resolved when the function is composed, not every time the function is run, but that's not what we have.


To support different units systems need a few base Si units and a value_as() function. If we assume that all unit systems have basic arithmetic for unit*unit, unit/unit, unit**int and scalar*unit then we can construct what we need.

Possibilities:

(a) Make a proxy interface so each quantity in the system (constant, attribute, parameter or return value) is appropriately wrapped. Depending on how you import the library (e.g., from periodictable.astropy import *) you will then get a different proxy. It'll be tricky to interleave this with other features, such as lazy loading of table attributes, private tables and pickling of elements.

(b) Modify the interface so that all quantities are treated as unit-like quantities. Initialize the unit system as a configuration entry on startup, then each function would ask the unit converter to translate inputs and outputs into the correct units. Default to a "unitless" system that accepts and returns simple quantities in the documented units so existing code doesn't break. This does mean that you pay for units even if you are not using them, but may be easier to maintain in the long run.

(c) Provide a parallel interface, with e.g., He.mass_u, returning mass of helium with units. Less surprising than having the values change type depending on what unit system is active, but makes for ugly variable names for the calling code.

@pkienzle
Copy link
Collaborator

A number of the values also have uncertainties. The space of uncertainties X units packages is even larger. Both need to be propagated through calculations.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants