Skip to content

Commit

Permalink
move some content from tutorial to new page
Browse files Browse the repository at this point in the history
this commit adds a new page to the docs about the various
ways of defining quantity objects in Pint, and moves some
of the content from the tutorial in there

not certain if it's a better arrangement, the theory is
that a more concise tutorial with links to more detailed
pages might get users up and running faster

very open to suggestions though
  • Loading branch information
clarkgwillison committed Jul 14, 2020
1 parent c2b51dc commit 3a1d475
Show file tree
Hide file tree
Showing 4 changed files with 194 additions and 102 deletions.
1 change: 0 additions & 1 deletion docs/contexts.rst
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
.. _contexts:

Contexts
========
Expand Down
142 changes: 142 additions & 0 deletions docs/defining-quantities.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
Defining Quantities
===================

A quantity in Pint is the product of a unit and a magnitude.

Pint supports several different ways of defining physical quantities, including
a powerful string parsing system. These methods are largely interchangeable,
though you may **need** to use the constructor form under certain circumstances
(see :doc:`nonmult` for an example of where the constructor form is required).

By multiplication
-----------------

If you've read the :ref:`Tutorial`, you're already familiar with defining a
quantity by multiplying a ``Unit()`` and a scalar:

.. doctest::

>>> from pint import UnitRegistry
>>> ureg = UnitRegistry()
>>> ureg.meter
<Unit('meter')>
>>> 30.0 * ureg.meter
<Quantity(30.0, 'meter')>

This works to build up complex units as well:

.. doctest::

>>> 9.8 * ureg.meter / ureg.second**2
<Quantity(9.8, 'meter / second ** 2')>


Using the constructor
---------------------

In some cases it is useful to define :class:`Quantity() <pint.quantity.Quantity>`
objects using it's class constructor. Using the constructor allows you to
specify the units and magnitude separately.

We typically abbreviate that constructor as `Q_` to make it's usage less verbose:

.. doctest::

>>> Q_ = ureg.Quantity
>>> Q_(1.78, ureg.meter)
<Quantity(1.78, 'meter')>

As you can see below, the multiplication and constructor methods should produce
the same results:

.. doctest::

>>> Q_(30.0, ureg.meter) == 30.0 * ureg.meter
True
>>> Q_(9.8, ureg.meter / ureg.second**2)
<Quantity(9.8, 'meter / second ** 2')>


Using string parsing
--------------------

Pint includes a powerful parser for detecting magnitudes and units (with or
without prefixes) in strings. Calling the ``UnitRegistry()`` directly
invokes the parsing function:

.. doctest::

>>> 30.0 * ureg('meter')
<Quantity(30.0, 'meter')>
>>> ureg('30.0 meters')
<Quantity(30.0, 'meter')>
>>> ureg('3000cm').to('meters')
<Quantity(30.0, 'meter')>

The parsing function is also available to the ``Quantity()`` constructor and
the various ``.to()`` methods:

.. doctest::

>>> Q_('30.0 meters')
<Quantity(30.0, 'meter')>
>>> Q_(30.0, 'meter')
<Quantity(30.0, 'meter')>
>>> Q_('3000.0cm').to('meter')
<Quantity(30.0, 'meter')>

Or as a standalone method on the ``UnitRegistry``:

.. doctest::

>>> 2.54 * ureg.parse_expression('centimeter')
<Quantity(2.54, 'centimeter')>

It is fairly good at detecting compound units:

.. doctest::

>>> g = ureg('9.8 meters/second**2')
>>> g
<Quantity(9.8, 'meter / second ** 2')>
>>> g.to('furlongs/fortnight**2')
<Quantity(7.12770743e+10, 'furlong / fortnight ** 2')>

And behaves well when given dimensionless quantities, which are parsed into
their appropriate objects:

.. doctest::

>>> ureg('2.54')
2.54
>>> type(ureg('2.54'))
<class 'float'>
>>> Q_('2.54')
<Quantity(2.54, 'dimensionless')>
>>> type(Q_('2.54'))
<class 'pint.quantity.build_quantity_class.<locals>.Quantity'>

.. note:: Pint's rule for parsing strings with a mixture of numbers and
units is that **units are treated with the same precedence as numbers**.

For example, the units of

.. doctest::

>>> Q_('3 l / 100 km')
<Quantity(0.03, 'kilometer * liter')>

may be unexpected at first but, are a consequence of applying this rule. Use
brackets to get the expected result:

.. doctest::

>>> Q_('3 l / (100 km)')
<Quantity(0.03, 'liter / kilometer')>

.. note:: Since version 0.7, Pint **does not** use eval_ under the hood.
This change removes the `serious security problems`_ that the system is
exposed to when parsing information from untrusted sources.

.. _eval: http://docs.python.org/3/library/functions.html#eval
.. _`serious security problems`: http://nedbatchelder.com/blog/201206/eval_really_is_dangerous.html
1 change: 1 addition & 0 deletions docs/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,7 @@ User Guide

getting
tutorial
defining-quantities
numpy
nonmult
wrapping
Expand Down
Loading

0 comments on commit 3a1d475

Please sign in to comment.