Skip to main content

Convenience class for doing maths with explicit coordinates

Project description

coordinates

Build Status Python Versions

Convenience class for dealing with coordinates which need both maths and explicit ordering.

Motivation

Numpy arrays are great for doing maths with coordinates stored as arrays.

Dicts are great for dealing with coordinate systems where the order keeps changing (e.g. between C and Fortran order).

But what if you want both?

(Note: if you're doing lots of maths... stick with numpy)

Installation

pip install coordinates

Usage

Coordinates are Mappings (i.e. dict-like). They don't expose an interface for mutation, but we're all consenting adults so if you really want to modify the internal _dict, I won't stop you.

Instantiation

They can be instantiated in any of the ways a dict can (from another Mapping, a sequence of pairs, some keyword arguments, or a mixture of the above).

from coordinates import Coordinate

Coordinate({'x': 1, 'y': 2})
Coordinate({'x': 1}, y=2)
Coordinate([('x', 1), ('y', 2)])
Coordinate(x=1, y=2)

If an order is defined (more on this later), you can also instantiate a Coordinate from a single argument which is a sequence, or from a number of *args.

Coordinate([1, 2], order='xy')
Coordinate(1, 2, order='xy')

Coordinate.default_order = 'xy'
Coordinate([1, 2])
Coordinate(1, 2)

Because Mappings can be instantiated from other Mappings, you can "extend" existing coordinates into new dimensions.

coord_2d = Coordinate(x=1, y=2)
coord_3d = Coordinate(coord_2d, z=3)

Finally, many Coordinates can be instantiated lazily using from_sequence:

Coordinate.from_sequence([(1, 2, 3), (3, 4, 5)], order='xyz')
Coordinate.from_sequence([{'x': 1, 'y': 2}, {'x': 3, 'y': 4}], z=10)

To note:

  • order-dependent instantiation is incompatible with **kwargs
  • Instantiation from a sequence of tuples will fail in 2D because it will be interpreted as key-value pairs. Use a comprehension here instead: Coordinate.from_sequence(zip('xy', row) for row in sequence)

Maths

Coordinates do maths like you might expect them to, where the other operand is anything dict-like with the same keys, or a number.

coord = Coordinate(x=1, y=2, z=3)

coord * 2 == Coordinate(x=2, y=4, z=6)
>>> True

coord ** 2 == Coordinate(x=1, y=4, z=9)
>>> True

coord + coord == Coordinate(x=2, y=4, z=3)
>>> True

coord += 1  # coord is a reference to a new object; no mutation
coord == Coordinate(x=2, y=3, z=4)
>>> True

abs(Coordinate(x=-10, y=10)) == Coordinate(x=10, y=10)
>>> True

import math
math.ceil(Coordinate(x=0.5)) == Coordinate(x=1)
>>> True

math.floor(Coordinate(x=0.5)) == Coordinate(x=0)
>>> True

They also have some convenience methods for getting the sum, product or norm of their keys.

coord.sum() == 9
>>> True

coord.prod() == 24
>>> True

Coordinate(x=3, y=4).norm(order=2) == 5
>>> True

Ordering

You can get the keys, values or items of the Coordinate in a specific order:

coord.to_list('yxz') == [2, 1, 3]
>>> True

list(coord.items('yxz')) == [('y', 2), ('x', 1), ('z', 3)]
>>> True

The default order for a single instance can be given on instantiation, or mutated (this does not affect equality).

The default order for all Coordinates can be set on the class. This affects existing instances, but does not override their order if it was set explicitly.

If neither an instance order or a class default_order is set, it falls back to reverse lexicographic.

coord3 = Coordinate(x=1, y=2, z=3, order='zxy')
coord3.order = 'yzx'

Coordinate.default_order = 'xyz'

Subclassing

If you're working in one space, the spaced_coordinate factory can create custom subclasses with a fixed set of keys and optionally a default order.

from coordinates import spaced_coordinate
CoordinateXYZC = spaced_coordinate('CoordinateXYZC', 'xyzc')

# this will raise a ValueError
CoordinateXYZC(x=1, y=2, z=3)

Or you can subclass Coordinate directly.

Value access

Coordinate values can be accessed with dict-like syntax (coord['x'], coord.get('y', 2)) or, for convenience, attribute-like (coord.z) if the keys are strings.

Note

If you don't want the order-related functionality for another application, the base class MathDict is implemented here too.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

coordinates-0.4.0.tar.gz (6.7 kB view details)

Uploaded Source

Built Distribution

coordinates-0.4.0-py2.py3-none-any.whl (7.0 kB view details)

Uploaded Python 2 Python 3

File details

Details for the file coordinates-0.4.0.tar.gz.

File metadata

  • Download URL: coordinates-0.4.0.tar.gz
  • Upload date:
  • Size: 6.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/3.1.1 pkginfo/1.5.0.1 requests/2.21.0 setuptools/40.8.0 requests-toolbelt/0.9.1 tqdm/4.31.1 CPython/3.7.3

File hashes

Hashes for coordinates-0.4.0.tar.gz
Algorithm Hash digest
SHA256 4014374183909b7bab3c4bfd691b6fcf17bc6063ab7b7307d0f0ababaacfdafa
MD5 b87331035efb1c9fab7f26b068f4d891
BLAKE2b-256 b1ed06617f24371b48875b3b24f5e558c5606daad2be7a00d0099a14b70636ad

See more details on using hashes here.

File details

Details for the file coordinates-0.4.0-py2.py3-none-any.whl.

File metadata

  • Download URL: coordinates-0.4.0-py2.py3-none-any.whl
  • Upload date:
  • Size: 7.0 kB
  • Tags: Python 2, Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/3.1.1 pkginfo/1.5.0.1 requests/2.21.0 setuptools/40.8.0 requests-toolbelt/0.9.1 tqdm/4.31.1 CPython/3.7.3

File hashes

Hashes for coordinates-0.4.0-py2.py3-none-any.whl
Algorithm Hash digest
SHA256 5dcab7b939f774e2a7ca1ac79af9f38233767d5a33bca5e0c7a7c9200450e636
MD5 0ecfcbf72c7651764c4c136302861630
BLAKE2b-256 7bd32882a9189ef47015661cf3eb38253dbe18e446da4d6f61f20080ad3ae930

See more details on using hashes here.

Supported by

AWS AWS Cloud computing and Security Sponsor Datadog Datadog Monitoring Fastly Fastly CDN Google Google Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Sentry Sentry Error logging StatusPage StatusPage Status page