1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
|
from typing import Any, TypeVar
import act4e_interfaces as I
from .sets_representation import MyFiniteSet, SolFiniteSetRepresentation
from .sets_product import MyFiniteSetProduct
from .maps_representation import MyFiniteMap, SolFiniteMapRepresentation
X = TypeVar("X")
class MyFiniteSemigroup(I.FiniteSemigroup[X]):
_carrier: I.FiniteSet[X]
_composition: I.FiniteMap[X, X]
def __init__(self, s: I.FiniteSet[X], f: I.FiniteMap[X, X]):
self._carrier = s
self._composition = f
def carrier(self) -> I.FiniteSet[X]:
return self._carrier
def composition(self) -> I.FiniteMap[X, X]:
return self._composition
def compose(self, a: X, b: X) -> X:
p = self._composition.source().pack([a, b])
return self._composition(p)
class MyFiniteMonoid(MyFiniteSemigroup, I.FiniteMonoid[X]):
_identity: X
def __init__(self, s: I.FiniteSet[X], f: I.FiniteMap[X, X], e: X):
super().__init__(s, f)
self._identity = e
# def compose(self, a: X, b: X) -> X:
# if self.carrier().equal(a, self._identity):
# return b
# elif self.carrier().equal(b, self._identity):
# return a
# else:
# return super().compose(a, b)
def identity(self) -> X:
return self._identity
class MyFiniteGroup(MyFiniteMonoid, I.FiniteGroup[X]):
_inverse: I.FiniteMap[X, X]
def __init__(self, s: I.FiniteSet[X], f: I.FiniteMap[X, X], e: X, i: I.FiniteMap[X, X]):
super().__init__(s, f, e)
self._inverse = i
def inverse(self, a: X):
return self._inverse(a)
class SolFiniteSemigroupRepresentation(I.FiniteSemigroupRepresentation):
def load(self, h: I.IOHelper, s: I.FiniteSemigroup_desc) -> I.FiniteSemigroup[Any]:
if not all(k in s.keys() for k in ["carrier", "composition"]):
raise I.InvalidFormat()
fsr = SolFiniteSetRepresentation()
A = fsr.load(h, s["carrier"])
# FIXME: maybe use this?
# fmr = SolFiniteMapRepresentation()
for inp, out in s["composition"]:
if not all(A.contains(i) for i in inp):
raise I.InvalidFormat()
if not A.contains(out):
raise I.InvalidFormat()
p = MyFiniteSetProduct([A, A])
f = MyFiniteMap(p, A, s["composition"])
return MyFiniteSemigroup(A, f)
def save(self, h: I.IOHelper, m: I.FiniteSemigroup[Any]) -> I.FiniteSemigroup_desc:
fsr = SolFiniteSetRepresentation()
fmr = SolFiniteMapRepresentation()
d = {"carrier": fsr.save(h, m.carrier()),
"composition": []}
for a in m.carrier().elements():
for b in m.carrier().elements():
e = m.composition().source().pack([a, b])
d["composition"].append([e, m.compose(a, b)])
return d
class SolFiniteMonoidRepresentation(I.FiniteMonoidRepresentation):
def load(self, h: I.IOHelper, s: I.FiniteMonoid_desc) -> I.FiniteMonoid[X]:
fsgr = SolFiniteSemigroupRepresentation()
semi = fsgr.load(h, s)
if not ("neutral" in s.keys()):
raise I.InvalidFormat()
e = s["neutral"]
if not semi.carrier().contains(e):
raise I.InvalidFormat()
return MyFiniteMonoid(semi.carrier(), semi.composition(), e)
def save(self, h: I.IOHelper, m: I.FiniteMonoid[Any]) -> I.FiniteMonoid_desc:
fsgr = SolFiniteSemigroupRepresentation()
d = fsgr.save(h, m)
d["neutral"] = m.identity()
return d
class SolFiniteGroupRepresentation(I.FiniteGroupRepresentation):
def load(self, h: I.IOHelper, s: I.FiniteGroup_desc) -> I.FiniteGroup[X]:
fmor = SolFiniteMonoidRepresentation()
m = fmor.load(h, s)
if not "inverse" in s.keys():
raise I.InvalidFormat()
i = MyFiniteMap(m.carrier(), m.carrier(), s["inverse"])
return MyFiniteGroup(m.carrier(), m.composition(), m.identity(), i)
def save(self, h: I.IOHelper, m: I.FiniteGroup[Any]) -> I.FiniteGroup_desc:
fmor = SolFiniteMonoidRepresentation()
d = fmor.save(h, m)
d["inverse"] = []
for c in m.carrier().elements():
d["inverse"].append([c, m.inverse(c)])
return d
|