Skip to content

Commit

Permalink
Merge pull request #212 from eric-wieser/linear-transformation
Browse files Browse the repository at this point in the history
Add transformation tools
  • Loading branch information
eric-wieser committed Apr 7, 2020
2 parents 26c333c + 8386fa3 commit 9977aef
Show file tree
Hide file tree
Showing 7 changed files with 477 additions and 43 deletions.
131 changes: 131 additions & 0 deletions clifford/test/test_transformations.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
import numpy as np
import pytest

from clifford import Layout, ConformalLayout, BasisVectorIds
from clifford import transformations


# fixtures make the test a little faster

@pytest.fixture(scope='module')
def g2():
return Layout([1, 1], ids=BasisVectorIds(['u', 'v']))


@pytest.fixture(scope='module')
def g2c(g2):
return ConformalLayout([1, 1, 1, -1], ids=BasisVectorIds(['u', 'v', 'p', 'm']), layout=g2)


@pytest.fixture(scope='module')
def g3():
return Layout([1, 1, 1], ids=BasisVectorIds(['x', 'y', 'z']))


class TestBetweenBasisVectors:
def test_same_layout(self, g3):
ex, ey, ez = g3.basis_vectors_lst
x = ex + 2*ey + 4*ex*ez

f = transformations.between_basis_vectors(g3, g3)
assert f(x) == x

f_swap = transformations.between_basis_vectors(g3, g3, {'x': 'y', 'y': 'z', 'z': 'x'})
assert f_swap(x) == ey + 2*ez + 4*ey*ex

def test_different_layout(self, g2, g2c, g3):
e1, e2 = g2.basis_vectors_lst
e1c, e2c, epc, emc = g2c.basis_vectors_lst

f = transformations.between_basis_vectors(g2, g2c)
x = 1 + 2*e1 + 3*e2 + 4*e1*e2
xc = 1 + 2*e1c + 3*e2c + 4*e1c*e2c
assert f(x) == xc
assert f.adjoint(xc) == x

ex, ey, ez = g3.basis_vectors_lst
f = transformations.between_basis_vectors(g2, g3, {'u': 'z', 'v': 'y'})
xs = 1 + 2*ez + 3*ey + 4*ez*ey
assert f(x) == xs
assert f.adjoint(xs) == x

# incorrect layout
with pytest.raises(ValueError):
f(xs)

# invalid basis
with pytest.raises(ValueError):
transformations.between_basis_vectors(g2, g3, {'fake': 'z', 'v': 'y'})
with pytest.raises(ValueError):
transformations.between_basis_vectors(g2, g3, {'u': 'z', 'v': 'fake'})


class TestOutermorphismMatrix:
def test_invariants(self, g2):
e1, e2 = g2.basis_vectors_lst

matrix = np.array([[ 0, 1],
[-1, 0]])
f = transformations.OutermorphismMatrix(matrix, g2)

# test the vector transform is as requested
assert f(e1) == -e2
assert f(e2) == e1
# test the generalization is correct
assert f(e1^e2) == f(e1)^f(e2)
assert f(g2.scalar) == g2.scalar

# test that distributivity is respected
assert f(g2.scalar + 2*e1 + 3*(e1^e2)) == f(g2.scalar) + 2*f(e1) + 3*f(e1^e2)

def test_between_layouts(self, g2, g3):
matrix = np.array([[1, 0],
[0, 1],
[0, 0]])
# arguments backwards
with pytest.raises(ValueError):
transformations.OutermorphismMatrix(matrix, g3, g2)

e1, e2 = g2.basis_vectors_lst
ex, ey, ez = g3.basis_vectors_lst

f = transformations.OutermorphismMatrix(matrix, g2, g3)
assert f(e1) == ex
assert f(e2) == ey


class TestLinearMatrix:
def test_same_layout(self, g2):
e1, e2 = g2.basis_vectors_lst

dual_matrix = np.array([
[ 0, 0, 0, 1],
[ 0, 0, 1, 0],
[ 0, -1, 0, 0],
[-1, 0, 0, 0]
])
f_dual = transformations.LinearMatrix(dual_matrix, g2)
x = 1 + 2*e2 + 3*e1*e2
assert f_dual(x) == x.dual()

def test_between_layouts(self, g2, g3):
matrix = np.array([[1, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 0],
[0, 0, 0, 0],
[0, 0, 0, 0],
[0, 0, 0, 0],
[0, 0, 0, 1]])

# arguments backwards
with pytest.raises(ValueError):
transformations.LinearMatrix(matrix, g3, g2)

e1, e2 = g2.basis_vectors_lst
ex, ey, ez = g3.basis_vectors_lst

f = transformations.LinearMatrix(matrix, g2, g3)
assert f(e1) == ex
assert f(e2) == ey
assert f(e1^e2) == ex^ey^ez

0 comments on commit 9977aef

Please sign in to comment.