This would be most compatible with other complement maps discussed here if the r degenerate bases appeared exclusively at (either) the beginning or end of your (p+q+r)pseudoscalar, no? If they are in the middle you could get some swapping which would change the polarity.
@Orbots actually, as I have explained previously, I donβt recommend working with degenerate metrics because it introduces these type of issues. Instead, if you used a first order symmetric basis as I discussed in other threads, then there would be no concern about the ordering of that index, since it is not anti-symmetric. However, for some reason people in this community insist in making the extra basis element anti-symmetric as a Grassmann element, but with degenerate metric. An alternative would be to recognize the additional foruth basis element as a symmetric basis instead (it commutes), as I have discussed before. This is also e.g. more consistent with first order Taylor expansion as I wrote in my paper.
For those of us unable to read your paper. I think this is what you mean by:
julia> basis"-+++"
(β¨-+++β©, v, vβ, vβ, vβ, vβ, vββ, vββ, vββ, vββ, vββ, vββ, vβββ, vβββ, vβββ, vβββ, vββββ)
julia> e0 = (1v1+1v2)/2
0.5vβ + 0.5vβ + 0.0vβ + 0.0vβ
julia> e0*e0
0.0vβ
Is this correct? You use two of your basis vectors with metric - and + to make e_0 which effectively has a metric of 0.
Actually this doesnβt seem to be what you are talking about: [quote=βchakravala, post:42, topic:128β]
it commutes
[/quote]
julia> 1v2*e0
0.5 - 0.5vββ
julia> e0*1v2
0.5 + 0.5vββ
Iβve had to go through this process recently so hereβs a little example I translated from my lib to Grassmann.jl, since Julia is my language of choice.
As described above in the excellent posts by @ninepoints, we want the map to be an involution J^2 = id. Also J(x) should βfill in the holesβ of J(x)*I.
Grassmann has something like the reciprocal basis I described above. You can switch back and forth using the '
operator.
Hereβs the J map for PGA(3)
using Grassmann
# specify PGA(3) metric with eβ as the degenerate metric
basis"+++0"
# J map
dual(x) = (x'*SubManifold(V'))'
# put unit basis blades into list
E = (1v1,1v2,1v3,1v4,1v12,1v13,1v14,1v23,1v24,1v34,1v234,1v134,1v124,1v123,1v1234)
# test the J map to see it's an involution.
zip(E, dual.(E), (dualβdual).(E)) |> collect
# result: ( original blade, dual(blade), dual(dual(blade)) )
(1vβ, -1vβββ, 1vβ)
(1vβ, 1vβββ, 1vβ)
(1vβ, -1vβββ, 1vβ)
(1vβ, 1vβββ, 1vβ)
(1vββ, -1vββ, 1vββ)
(1vββ, 1vββ, 1vββ)
(1vββ, -1vββ, 1vββ)
(1vββ, -1vββ, 1vββ)
(1vββ, 1vββ, 1vββ)
(1vββ, -1vββ, 1vββ)
(1vβββ, -1vβ, 1vβββ)
(1vβββ, 1vβ, 1vβββ)
(1vβββ, -1vβ, 1vβββ)
(1vβββ, 1vβ, 1vβββ)
(1vββββ, 1v, 1vββββ)
# now we use this map above build our objects in dual space with correct signs
# e.g. entry for v234 is -, so we use -x*1v234
point(x, y, z, w=1) = -x*1v234 + y*1v134 - z*1v124 + w*1v123
p = point(-1.0,2.0,3.0)
1.0vβββ - 3.0vβββ + 2.0vβββ + 1.0vβββ
# signs for coordinates in standard space are what you would expect.
dual(p)
0.0 - 1.0vβ + 2.0vβ + 3.0vβ + 1.0vβ
Iβve done a few things differently here. These are design choices, not βcorrectβ or βincorrectβ math. Again, just my personal preference, not the right way to do things, nor the wrong way. Maybe a little opinionated.
First, I wanted the homogeneous coordinate in the familiar w component of a coordinate vector. Yes, I care about coordinates, thatβs what computers work with.
Second, we donβt really care for cyclical ordering, our implementation and cognitive load prefer sorted.
Third, I wanted coordinates in the standard space to be easily read-off without any mental sign flips. The suggestion to view points as an intersection of 3 planes in dual space is unintuitive⦠who triangulates positions when you can just not?
Fourth we want a simple way to figure out when/where signs flip.
You can see weβve achieved our first three goals with basis"+++0"
, dual
and point
.
Last goal is achieved by looking at the map I created above. Or better yet, take the tetrahedron from @ninepoints post and add signs.
Consistently orient edges from lower index to higher index.
Add a little + or - by vertices that end up with a + or - from our map.
Edge signs are simply the parity of the two verts on that edge. ie. sign(edge12) is sign(vertex1)*sign(vertex2)
Face signs are the same as the opposing vertex.
Make the origin the homogeneous coord, so your e1,e2,e3 basis visually match x,y,z axis.
Iβd draw a picture, but my programmer art is probably worse than no art.
Hope this helps.
@Orbots, there are several aspects of (specifically) my library that you are misunderstanding in your last 2 posts, Iβll respond later when I get around to it!
@chakravala my intention was to show how to easily create a grade reversing involution ( J, the duality map ) with the same metric signature used in popular PGA literature using a Geometric Algebra library not designed specifically for PGA.
If I got something wrong let me know.
Iβm new here, and newbie, and had the same question.
I have read the initial chapters of Brownβs amazing book a long time ago, so Iβm going to apply that reasoning to try to explain why
1, e0, e1, e2, e3, e01, e02, e03, e12, e31, e23, e021, e013, e032. e123, e0123
are picked as the basis elements
Each basis element is picked in such a way that Grassmannβs βErgΓ€nzungβ aka βcomplementβ in Browns book of that element is again a basis element.
The elements are picked in such a way so that:
- the complement of the scalar 1 is the pseudo-scalar eββββ
- the complement of the origin eβββ is the ideal plane eβ
- the complement of the βYZβ plane eβ is the βXβ direction eβββ
- the complement of the βZXβ plane eβ is the βYβ direction eβββ
- the complement of the βXYβ plane eβ is the βZβ direction eβββ
- the complement of the βZβ axis eββ is the ideal line eββ (ideal line in the βXYβ plane)
etc
If I recall correctly, the complement C(E) of any element E is defined in such a way that
E β§ C(E) = I
In PGA, this would be
E β§ C(E) = eββββ
where
eββββ = eβ β§ eβ β§ eβ β§ eβ
And remember β§ is anti-commutative, so
eα΅’β±Ό = eα΅’ β§ eβ±Ό = -eβ±Ό β§ eα΅’ = -eβ±Όα΅’
So the complement of each basis element is (Iβll only flip one pair at the time)
C(1) = eββββ because 1 β§ eββββ = eββββ
C(eβ) = eβββ because eβ β§ eβββ = eββββ
C(eβ) = eβββ because eβ β§ eβββ = eββββ = -eββββ = eββββ
C(eβ) = eβββ because eβ β§ eβββ = eββββ = -eββββ = eββββ
C(eβ) = eβββ because eβ β§ eβββ = eββββ = -eββββ = eββββ = -eββββ = eββββ
C(eββ) = eββ because eββ β§ eββ = eββββ
C(eββ) = eββ because eββ β§ eββ = eββββ = -eββββ = eββββ = -eββββ = eββββ
C(eββ) = eββ because eββ β§ eββ = eββββ = -eββββ = eββββ
C(eββ) = eββ because eββ β§ eββ = eββββ = -eββββ = eββββ
etcβ¦
Because we happen to have 4 basis 1-elements in 3D PGA, an even number, the complement of the complement is again the complement, so that works out nicely. If the number of basis 1-elements is odd, the complement of the complement would have a sign flip.
I havenβt read any of the threads here, and Iβm new to PGA, so this might be completely wrong
Iβm currently trying to port Klein to C#, so Iβm trying to get a better understanding.