Skip to main content

para español

Observing Ordered Dictionary

The observing ordered dictionary is a datastructure for accessing child-elements by name or position. It is meant to be inherited (or composed: I inherit it in my applications, but it's almost composed given I override and rename every public method).

Parent objects (Observer()) will register themselves with their child elements (Observed()), who can notify the parent object of changes to its (the child's) properties. The classes are combined by the class Item(Observer, Observed).

It is well, if not chaotically, tested.

NB: While Observer() supports iteration and len(), indexing by [] is not supported yet.

Basic Use:

import ood

o = ood.Observer(*items_to_add)
o.add_items(*items_to_add)
o.pop_items(*items_to_pop) # returns list
o.get_items(*selectors) # returns list
o.get_item(selector) # see Selectors section below
o.has_item(selector)
o.reorder_all_items([selectors])
o.move_items(*selectors, ...) # must have one of before=, after=, position=, distance=

Children must inherit class Observed(), whose __init__(self, **kwargs) takes a name argument, and will supply methods get_name() and set_name():

import ood

o = Observed(name = "test")
o.get_name() == "test" # True
o.set_name("test2")
o.get_name() == "test2" # True

Also supplied are other internal _functions() used in parent-child communication.

Selectors

A primitive selector is either an int (the position of the child) or a str (the name of the child).

There is also a class Selector(), which is inherited by three other classes (two from ood.selectors) you can use:

Classes 1, 2

import ood
import ood.selectors as s

# Class 1:
# Select which child precisely if children w/ same name are allowed.
# Ordered by insertion.
s.Name_I(child_name str, child_index int)

# Class 2:
# Select children which they themselves have specified children.
s.Has_Child(selector) # 

Class 3:

All Observed are also selectors which specify to return themselves. Example:

import ood

child = ood.Observed("A")
not_child = ood.Observed("B")
parent = ood.Observer(child)

parent.has_item(child)  # True
parent.has_item("A")    # True
parent.has_item(0)      # True, useless.

parent.has_item(not_child)  # False
parent.has_item("B")        # False
parent.has_item(1)          # False

Configuration Settings:

ood.exceptions has ErrorLevel.IGNORE, ErrorLevel.WARN and ErrorLevel.ERROR. True is also ERROR and False is IGNORE.

The default values are shown below, they can be overridden:

import ood.exception as err

# Do non-existing indices to get_item(s), pop_items produce errors or empty array (or None)?
err.StrictIndexException.default_level = err.ErrorLevel.IGNORE

# Can one child have multiple parents?
err.MultiParentException = err.ErrorLevel.ERROR # WARN not possible

# Can multiple children of one parent have the same name?
err.NameConflictException = err.ErrorLevel.ERROR # WARN not possible

# Do we warn or error if you add the same child twice?
err.RedundantAddException = err.ErrorLevel.WARN

Extending

If you inhert Observer() or Item(), you can override class variables _type and _child_type, exceptions generated will use those terms instead of "item" when raising exceptions.

class RedNodes(ood.Item):
    _type="RedNode"
    _child_type="Node"
    def __init__(self, *args, **kwargs):
        _my_vars = kwargs.pop("key", "default_value") # Popping is important! Don't pass weird stuff to ood!
        super().__init__(*args, **kwargs)
        ... # Do whatever you want

    def get_node(self, selector, **kwargs):
        return super().get_item(self, selector, **kwargs)
    
    ... # etc

Adding more observed variables:

Children can call _notify_parents(parameter=..., old_parameter=...), where parameter would be the parameter that changes. For example, set_name("new_name") calls _notify_parents(self, name="new_name", old_name="old_name").

On the parent side, you must implement

o._child_options(self, child, **kwargs) 
o._child_update(self, child, **kwargs)

_child_options() should raise an exception, and the child should understand that the parameter change will not be accepted. (this is used in case the configuration is set that two children cannot have the same name).

def set_name(self, name):
    old_name = self.get_name()
    self._name = name
    try:
        _notify_parents(self, old_name=old_name, name=name)
    except:
        self._name = old_name
        raise Exception("Can't change name!")

Release files for ood 1.0.9

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for ood 1.0.9
File Size Uploaded
ood-1.0.9.tar.gz 16.2 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for ood 1.0.9
File Interpreter ABI Platform
ood-1.0.9-py3-none-any.whl Python 3 none any Details

Total release size: 25.3 kB

Release files / ood-1.0.9.tar.gz

Download URL ood-1.0.9.tar.gz
Size 16.2 kB
Tags Source
SHA-256 checksum
How to use checksums
05315fb8cccf59c42ec3f99b7f04554b97a7e43ef03810469041369071f88b50
BLAKE2b-256 checksum
How to use checksums
63121a3de67fe95ede8253c46e7f0e8603dd2c05a1b40419cef6f2a04c51e57e
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/5.0.0 CPython/3.12.2

Release files / ood-1.0.9-py3-none-any.whl

Download URL ood-1.0.9-py3-none-any.whl
Size 9.1 kB
Tags Python 3
SHA-256 checksum
How to use checksums
5e93336a5760657d499ca2a450b9daee6c72c41b305f4bc84a50902b1e28c8c9
BLAKE2b-256 checksum
How to use checksums
afac3eefd08adfb0077a27f8151416b4f347b42dcc729e899fbafacc073bf047
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/5.0.0 CPython/3.12.2

Release history Release notifications | RSS feed

This release

1.0.9 This release

2 release files

1.0.6

2 release files

1.0.5

2 release files

1.0.4

2 release files

1.0.3

2 release files

1.0.0

2 release files

0.99.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page