[ANN]: Multivectors.jl

Announcing Multivectors.jl. A package implementing Geometric Algebra with positive, negative and degenerate metric signatures.

9 Likes

Very cool, glad to see more packages exploring this space! If you’re interested, I’d be happy to collaborate with you at some point on this package if you’re interested. What sort of work would you like to see happen in this space in the near future?

One thing I’ve noticed is that it seems that your Multivectors are not of a static dimensionality. That’s an interesting choice and while I can see advantages, I think there are great advantages to having the dimension of the algebra be encoded in the type of the Multivector. This lets you do things like unroll multiplications between multivectors, and I don’t think it’s an especially common usecase to multiply elements of geometric algebras of different dimensions. There was a discussion of this here: Encoding group elements and operations - #17 by Mason

where I showed the advantage of the unrolling. Here’s a comparison between the multiplication I hackily implemented in https://github.com/MasonProtter/GeometricAlgebras.jl and the multiplication in Multivectors.jl for a 3 dimensional geometric algebra:

using GeometricAlgebras
s, γ1, γ2, γ3 = basis_vectors(3)

A = s + γ1 + 2γ2 - γ3
B = γ1*γ2 - 3s
#--------------------------------
using Multivectors
@generate_basis("+++")

C = 1 + 1e₁ + 2e₂ - 1e₃
D = 1e₁*1e₂ - 3
#--------------------------------
f(A, B) = A*(A*A + B*B)*B

julia> @btime f($A, $B)
  92.291 ns (0 allocations: 0 bytes)
-75.0 + -115.0γ₁ + -55.0γ₂ + 45.0γ₃ + 45.0γ₁γ₂ + -35.0γ₁γ₂γ₃

julia> @btime f($C, $D)
  70.279 μs (1190 allocations: 33.17 KiB)
Multivector{Int64,3}
⟨-75⟩₀ + ⟨-55e₂,-115e₁,45e₃⟩₁ + ⟨45e₁₂,0e₁₃,0e₂₃⟩₂ + ⟨-35e₁₂₃⟩₃

One could maybe think of what I did as being like StaticArrays.jl, whereas your Multivectors are more akin to regular, dynamically sized arrays.

3 Likes

@Mason collaboration would be most welcome!

Performance of the Multivector and ( to a lesser extent ) of the KVector type is pretty sub-optimal, as you’ve noticed.

More than happy to accept pull requests that address that issue.

You have some specific interests in the field of Geometric Algebra?

I kept Multivector as general as possible because I’m still exploring applictions. I’m interested in applying Geometric Algebra to Discrete Differential Geometry. Still figuring out what algebra’s and objects are most useful there.

Initially I was interested in Blades and KVector types being separate packages that could be used without Multivectors. In practice I seem to always bring some Multivectors along though.

So Multivectors.jl was built bottom up from Blades, where you’ve appeared to take more of a top-down approach in GeometricAlgebras.jl.

Possibly this is useful in Differential Geometry. If you actually want to multiply elements from different algebras to implement, i.e. sensible push-forward or pull-back operations seems doubtful though. Could work out promotion rules to make something like that work nicely. So I reckon that’s a reasonable constraint to add.

You are getting really good performance there!

Left to my own devices, I was thinking of implementing yet another Type to represent k-vector + scalar or k-vector + pseudoscalar in an optimal fashion. I think there’s a name for these objects. Anyways, they are by far the most common kind of Multivector.
Starting to get a bit of a type explosion in Multivectors.jl though so just having a much faster Multivector type would probably be better.

Grassmann.jl is already designed in a way that allows geometric algebras of different dimension to interact by using the SubManifold from DirectSum.jl.

Also, I have implemented the suggestion given to me by @Mason also mentioned above, thanks! It only works for 5 dimensional geometric algebras or less, above that it’s slower than my high dimensional method.

1 Like