🐍 Numerical Description#
Predicates#
HalfSpace predicate#
The HalfSpace predicate can be used to test whether an individual lies in a half-space.
[1]:
from galactic.algebras.concept.core import Item
from galactic.algebras.convex.characteristics.core import Component, Number
from galactic.algebras.convex.descriptions.numerical.hull.core import HalfSpace
halfspace = HalfSpace(
space=(
Number(
components=(Component(expr="[0]"),),
name="x",
),
Number(
components=(Component(expr="[1]"),),
name="y",
),
),
a=1,
b=2,
c=3,
)
str(halfspace)
[1]:
'x + 2⋅y + 3 ≤ 0'
[2]:
halfspace(Item(value=[0, 1]))
[2]:
False
[3]:
halfspace(Item(value=[0, -3]))
[3]:
True
Segment predicate#
The Segment predicate can be used to test whether an individual lies on a segment.
[4]:
from galactic.algebras.concept.core import Item
from galactic.algebras.convex.characteristics.core import Component, Number
from galactic.algebras.convex.descriptions.numerical.hull.core import Segment
segment = Segment(
space=(
Number(
components=(Component(expr="[0]"),),
name="x",
),
Number(
components=(Component(expr="[1]"),),
name="y",
),
),
x1=1,
y1=2,
x2=3,
y2=4,
)
str(segment)
[4]:
'(x, y) ∈ Segment((1, 2), (3, 4))'
[5]:
segment(Item(value=[2, 3]))
[5]:
True
[6]:
segment(Item(value=[0, 0]))
[6]:
False
[7]:
segment(Item(value=[1, 2]))
[7]:
True
[8]:
segment(Item(value=[2, 3]))
[8]:
True
Descriptions#
NumericalDescription#
A NumericalDescription can describe a collection of individuals by computing the convex hull of numerical characteristics.
In the general case, if the number of numerical characteristics is:
1: it produces intervals on the real line.
2: it produces polygons in \(\mathbb{R}^2\).
[9]:
from galactic.algebras.convex.characteristics.core import Component, Number
from galactic.algebras.convex.descriptions.numerical.hull.core import (
NumericalDescription,
)
characteristic = Number(components=(Component(),))
description = NumericalDescription(space=(characteristic,))
[10]:
[str(attr) for attr in description([Item(value=1), Item(value=2)])]
[10]:
['float(@) ≥ 1.0', 'float(@) ≤ 2.0']
[11]:
[str(attr) for attr in description([Item(value=1)])]
[11]:
['float(@) = 1.0']
[12]:
[str(attr) for attr in description([Item(value="nan")])]
[12]:
[]
[13]:
[str(attr) for attr in description([])]
[13]:
['⊥']
[14]:
from galactic.algebras.concept.core import Item
from galactic.algebras.convex.characteristics.core import Component, Number
from galactic.algebras.convex.descriptions.numerical.hull.core import (
NumericalDescription,
)
x = Number(components=(Component(expr="[0]"),), name="x")
y = Number(components=(Component(expr="[1]"),), name="y")
description = NumericalDescription(space=(x, y))
[15]:
[
str(attr)
for attr in description(
[
Item(value=[0, 1]),
Item(value=[1, 1]),
Item(value=[2, 2]),
],
)
]
[15]:
['-0.447214⋅x + 0.894427⋅y - 0.894427 ≤ 0',
'-y + 1 ≤ 0',
'0.707107⋅x - 0.707107⋅y ≤ 0']
[16]:
[
str(attr)
for attr in description(
[
Item(value=[0, 1]),
Item(value=[1, 1]),
Item(value=[2, 1]),
],
)
]
[16]:
['(x, y) ∈ Segment((0, 1), (2, 1))']
[17]:
[
str(attr)
for attr in description(
[
Item(value=[0, 1]),
],
)
]
[17]:
['(x, y) = (0.0, 1.0)']
Concepts#
[18]:
from galactic.algebras.concept.core import ItemUniverse
from galactic.algebras.convex.characteristics.core import Component, Number
from galactic.algebras.convex.descriptions.core import (
Concept,
Context,
GaloisConnection,
PredicateUniverse,
)
from galactic.algebras.convex.descriptions.numerical.hull.core import (
NumericalDescription,
)
x = Number(components=(Component(expr="[0]"),), name="x")
y = Number(components=(Component(expr="[1]"),), name="y")
description = NumericalDescription(space=(x, y))
dataset = [[0, 0], [1, 0], [1, 1]]
context = Context(
ItemUniverse(dataset),
PredicateUniverse(descriptions=(description,)),
)
connection = GaloisConnection(context)
[19]:
list(context.domain)
[19]:
[Item(key=0, value=<list object at 0x7e887e97a3c0>),
Item(key=1, value=<list object at 0x7e887ea0a0c0>),
Item(key=2, value=<list object at 0x7e887e97a8c0>)]
[20]:
top = Concept(connection)
[21]:
list(top.extent)
[21]:
[Item(key=0, value=<list object at 0x7e887e97a3c0>),
Item(key=1, value=<list object at 0x7e887ea0a0c0>),
Item(key=2, value=<list object at 0x7e887e97a8c0>)]
[22]:
[str(attr) for attr in top.intent]
[22]:
['-y ≤ 0', '-0.707107⋅x + 0.707107⋅y ≤ 0', 'x - 1 ≤ 0']
[23]:
bot = Concept(connection, items=[])
[24]:
list(bot.extent)
[24]:
[]
[25]:
[str(attr) for attr in bot.intent]
[25]:
['⊥']
[26]:
from galactic.algebras.concept.core import ExtensibleLattice
from galactic.algebras.concept.renderer import (
ConceptRenderer,
ConceptHasseDiagramDrawer,
)
from galactic.algebras.convex.strategies.core import NaiveStrategy
lattice = ExtensibleLattice()
drawer = ConceptHasseDiagramDrawer(domain_renderer=ConceptRenderer())
drawer.draw(lattice)
[26]:
[27]:
lattice.extend([top])
drawer.draw(lattice)
[27]:
[28]:
lattice.extend([bot])
drawer.draw(lattice)
[28]:
[29]:
strategy = NaiveStrategy(descriptions=(description,))
predecessors = list(strategy(top))
display(predecessors)
[<galactic.algebras.convex.descriptions.core.Concept object at 0x7e887e2657c0>,
<galactic.algebras.convex.descriptions.core.Concept object at 0x7e887e046d50>,
<galactic.algebras.convex.descriptions.core.Concept object at 0x7e88b22ee6c0>]
[30]:
lattice.extend([predecessors[0]])
drawer.draw(lattice)
[30]:
[31]:
lattice.extend([predecessors[1]])
drawer.draw(lattice)
[31]:
[32]:
lattice.extend([predecessors[2]])
drawer.draw(lattice)
[32]: