Geometric algebra: Difference between revisions

Added FreeBASIC
(Rename Perl 6 -> Raku, alphabetize, minor clean-up)
(Added FreeBASIC)
 
(11 intermediate revisions by 6 users not shown)
Line 1:
{{draft task}}
 
'''Geometric algebra''' is an otheranother name for [[wp:Clifford algebra|Clifford algebra]]s and it's basically an algebra containing a vector space <math>\mathcal{V}</math> and obeying the following axioms:
 
:<math>\begin{array}{c}
Line 13:
The product operation in such algebra is called the ''geometric product''. Elements are called ''multivectors'', while multivectors in <math>\mathcal{V}</math> are just called ''vectors''.
 
There are a few simple examples of geometric algebras. A trivial one for instance is simply <math>\R</math>, where <math>\mathcal{V} = \R</math>. The complex numbers also form a geometric algebra, where the vector space is the one-dimensional space of all purely imaginary numbers. An otherAnother example is the space of [[Quaternion type|quaternions]], where the vector space is the three-dimensional space of all linear combinations of <math>(i, j, k)</math>.
 
The purpose of this task is to implement a geometric algebra with a vector space <math>\mathcal{V}</math> of dimension ''n'' of at least five, but for extra-credit you can implement a version with ''n'' arbitrary large. Using a dimension five is useful as it is the dimension required for the so-called ''conformal model'' which will be the subject of a derived task.
Line 55:
=={{header|C sharp|C#}}==
{{trans|D}}
<langsyntaxhighlight lang="csharp">using System;
using System.Text;
 
Line 237:
}
}
}</langsyntaxhighlight>
{{out}}
<pre>[-2.7059639813936, -2.65443237395364, -1.03355975191747, 5.431067101183, 9.57183741787636, 7.41390675997241, -8.09043009371666, -7.30180304927878, -1.50642825479215, -4.14594595273162, -1.78857280373918, -0.484382016930444, -7.42401696794793, -4.78491995868705, -8.43252648860165, -4.47485336471182, -2.3458119817208, 3.6184495826099, -7.50802924695147, -2.10106278080463, 7.15782745037037, 7.60049996423655, -10.6945339837475, -6.9874232887485, -4.85603010723139, -9.8225346377117, 3.50534384939214, 3.08239272713895, -9.92019737517891, -10.1065306142574, -8.79795495448311, -4.01442257971653]
Line 252:
=={{header|C++}}==
{{trans|D}}
<langsyntaxhighlight lang="cpp">#include <algorithm>
#include <iostream>
#include <random>
Line 419:
 
return 0;
}</langsyntaxhighlight>
{{out}}
<pre>[-5.63542, -6.59107, -10.2043, -5.21095, 8.68946, 0.579114, -4.67295, -6.72461, 1.55005, -2.63952, -1.83855, 2.4967, -4.3396, -9.9157, -4.6942, -3.23625, -2.3767, -4.55607, -14.3135, -14.2001, 9.84839, 3.69933, -3.38306, -7.60063, -0.236772, 0.988399, -0.549176, 6.61959, 4.69712, -5.34606, -12.2294, -12.6537]
Line 434:
=={{header|D}}==
{{trans|Kotlin}}
<langsyntaxhighlight lang="d">import std.exception;
import std.random;
import std.stdio;
Line 586:
// x^2 is real
writeln(x * x);
}</langsyntaxhighlight>
{{out}}
<pre>Vector([-4.60357, -1.66951, 0.230125, -4.36372, 11.0032, 7.21226, -1.5373, -6.44947, -5.07115, -1.63098, 2.90828, 7.1582, -15.5565, -1.31705, 1.3186, -1.07552, -4.04055, -2.16556, -4.41229, 0.323326, 5.03127, -1.36494, -0.915379, -6.86147, -5.87756, -4.31528, 12.4005, 15.6349, -9.54983, -1.08376, 3.60886, 4.17844])
Line 602:
We build a CGA based upon a generating quadratic form in R^n. The implementation is general enough, that is ei*ei = +/- 1 , and not restricted to 1. The 5 dimension limit comes from the use of 32 bits numbers to generate all permutations 101... , but this could be improved. The multi-vector multiplication is based on a multiplication table 2^n * 2^n , generated once for all.
 
<langsyntaxhighlight lang="scheme">
(define e-bits (build-vector 32 (lambda(i) (arithmetic-shift 1 i)))) ;; 1,2,4,..
(define (e-index i) ;; index of ei in native vector
Line 715:
</syntaxhighlight>
</lang>
{{out}}
<langsyntaxhighlight lang="scheme">
;; we use indices (1 ... n) in conformity with the Wikipedia reference
 
Line 767:
(• II J K) → -1*1
 
</syntaxhighlight>
</lang>
Multiplication table for A(3 0)
 
Line 820:
<br> <b>e</b>1<b>e</b>2<b>e</b>3 * <b>e</b>2<b>e</b>3 = - <b>e</b>1
<br> <b>e</b>1<b>e</b>2<b>e</b>3 * <b>e</b>1<b>e</b>2<b>e</b>3 = - <b>1</b>
 
=={{header|FreeBASIC}}==
{{trans|Wren}}
<syntaxhighlight lang="vbnet">Type Vector
dims(31) As Single
End Type
 
Function bitCount(i As Integer) As Integer
i = i - ((i Shr 1) And &h55555555)
i = (i And &h33333333) + ((i Shr 2) And &h33333333)
i = (i + (i Shr 4)) And &h0f0f0f0f
i = i + (i Shr 8)
i = i + (i Shr 16)
Return i And &h0000003F
End Function
 
Function ReorderingSign(i As Integer, j As Integer) As Integer
Dim As Integer k = i Shr 1
Dim As Integer sum = 0
While (k <> 0)
sum += bitCount(k And j)
k Shr= 1
Wend
Return Iif((sum And 1) = 0, 1, -1)
End Function
 
Function dot(lhs As Vector, rhs As Vector) As Vector
Dim result As Vector
For i As Integer = 0 To 31
result.dims(i) = 0.5 * (lhs.dims(i) * rhs.dims(i) + rhs.dims(i) * lhs.dims(i))
Next i
Return result
End Function
 
Function addition(lhs As Vector, rhs As Vector) As Vector
Dim result As Vector
For i As Integer = 0 To 31
result.dims(i) = lhs.dims(i) + rhs.dims(i)
Next i
Return result
End Function
 
Function multiply(lhs As Vector, rhs As Vector) As Vector
Dim result As Vector
Dim As Single s
Dim As Integer i, j, k
For i = 0 To 31
If lhs.dims(i) <> 0 Then
For j = 0 To 31
If rhs.dims(j) <> 0 Then
s = ReorderingSign(i, j) * lhs.dims(i) * rhs.dims(j)
k = i Xor j
result.dims(k) += s
End If
Next j
End If
Next i
Return result
End Function
 
Function multiplyScalar(lhs As Vector, rhs As Single) As Vector
Dim result As Vector
For i As Integer = 0 To 31
result.dims(i) = lhs.dims(i) * rhs
Next i
Return result
End Function
 
Function e(n As Integer) As Vector
If n > 4 Then Print "n must be less than 5": End
Dim result As Vector
result.dims(1 Shl n) = 1
Return result
End Function
 
Function randomVector() As Vector
Dim result As Vector
For i As Integer = 0 To 4
result = addition(result, multiplyScalar(e(i), Rnd))
Next i
Return result
End Function
 
Function randomMultiVector() As Vector
Dim result As Vector
For i As Integer = 0 To 31
result.dims(i) = Rnd
Next i
Return result
End Function
 
Randomize Timer
Dim a As Vector = randomMultiVector()
Dim b As Vector = randomMultiVector()
Dim c As Vector = randomMultiVector()
Dim x As Vector = randomVector()
 
' (ab)c == a(bc)
Print (multiply(multiply(a, b), c).dims(0))
Print (multiply(a, multiply(b, c)).dims(0))
Print
 
' a(b+c) == ab + ac
Print (multiply(a, addition(b, c)).dims(0))
Print (addition(multiply(a, b), multiply(a, c)).dims(0))
Print
 
' (a+b)c == ac + bc
Print (multiply(addition(a, b), c).dims(0))
Print (addition(multiply(a, c), multiply(b, c)).dims(0))
Print
 
' x^2 is real
Print (multiply(x, x).dims(0))
 
Sleep</syntaxhighlight>
 
=={{header|Go}}==
{{trans|JavaScript}}
<langsyntaxhighlight lang="go">package main
 
import (
Line 950 ⟶ 1,066:
// x² is real
fmt.Println(mul(x, x))
}</langsyntaxhighlight>
 
{{out}}
Line 970 ⟶ 1,086:
Implementation:
 
<langsyntaxhighlight Jlang="j">NB. indices are signed machine integers
vzero=: 1 $.2^31+IF64*32
odim=. 2^.#vzero
Line 1,003 ⟶ 1,119:
 
obasis=:1 (2^i.odim)ndx01 vzero
e=: {&obasis</langsyntaxhighlight>
 
Explanation:
Line 1,027 ⟶ 1,143:
Task examples:
 
<langsyntaxhighlight Jlang="j"> NB. test arbitrary vector being real (and having the specified result)
clean gmul~ +/ (e 0 1 2 3 4) gmul 1 _1 2 3 _2 (0 ndx01) vzero
0 │ 19
Line 1,070 ⟶ 1,186:
I gmul J+K
10 │ 1
12 │ _1</langsyntaxhighlight>
 
Note that sparse arrays display as <code>indices | value</code> for elements which are not the default element (0).
Line 1,078 ⟶ 1,194:
=={{header|Java}}==
{{trans|Kotlin}}
<langsyntaxhighlight lang="java">import java.util.Arrays;
import java.util.Random;
 
Line 1,235 ⟶ 1,351:
System.out.println(x.times(x));
}
}</langsyntaxhighlight>
{{out}}
<pre>(-14.826385115483191, -10.223187918212313, -15.02996653452487, -14.46670632198489, 9.367877413249497, 16.476783705852135, -15.946557036515442, -6.398255774639048, 1.5560496352407314, -7.135570742872677, -3.926278194944716, 4.7948511296793646, -8.132546330778185, -6.8139397609050025, -4.203632573891533, -0.5216302370612196, -11.240590807272154, -4.724378457579242, -16.477497153082254, -16.781194046381223, 3.715894934067395, 14.220125782905383, -12.846081825616357, -2.8313637859206557, 3.149468439469149, -5.163082715280577, -7.174869565605504, -3.34527279512389, -11.232806169860876, -9.975821980348016, -3.7795503524017735, -1.0610782061627755)
Line 1,249 ⟶ 1,365:
 
=={{header|javascript}}==
<langsyntaxhighlight lang="javascript">var GA = function () {
function e(n) {
var result = [];
result[1 << n] = 1;
return result;
}
function cdot(a, b) { return mul([0.5], add(mul(a, b), mul(b, a))) }
function neg(x) { return mul([-1], x) }
function bitCount(i) {
// Note that unsigned shifting (>>>) is not required.
i = i - ((i >> 1) & 0x55555555);
i = (i & 0x33333333) + ((i >> 2) & 0x33333333);
i = (i + (i >> 4)) & 0x0F0F0F0F;
i = i + (i >> 8);
i = i + (i >> 16);
return i & 0x0000003F;
}
function reorderingSign(a, b) {
a >>= 1;
var sum = 0;
while (a != 0) {
sum += bitCount(a & b);
a >>= 1;
}
}
return (sum & 1) == 0 ? 1 : -1;
}
function add(a, b) {
var result = a.slice(0);
for (var i in b) {
if (result[i]) {
result[i] += b[i];
} else {
result[i] = b[i];
}
}
}
return result;
}
function mul(a, b)
{
var result = [];
for (var i in a) {
if (a[i]) {
for (var j in b) {
if (b[j]) {
var s = reorderingSign(i, j) * a[i] * b[j];
// if (i == 1 && j == 1) { s *= -1 } // e0*e0 == -1
var k = i ^ j;
if (result[k]) {
result[k] += s;
} else {
result[k] = s;
}
}
}
}
}
}
}
}
return result;
}
return {
e : e,
cdot : cdot,
neg : neg,
add : add,
mul : mul
};
}();</lang>
</syntaxhighlight>
 
And then, from the console:
 
<langsyntaxhighlight lang="javascript">var e = GA.e, cdot = GA.cdot;
for (var i = 0; i < 5; i++) {
Line 1,357 ⟶ 1,474:
 
// x² is real
console.log(GA.mul(x, x));</langsyntaxhighlight>
{{out}}
<pre>[-7.834854130554672, -10.179405417124476, 5.696414143584243, -1.4014556169803851, 12.334288331422336, 11.690738709598888, -0.4279888274147221, 6.226618790084965, -10.904144874917206, -5.46919448234424, -5.647472225071031, -2.9801969751721744, -8.284532508545746, -3.3280413654836494, -2.2182526412098493, 0.4191036292473347, 3.0485450100607103, -0.20619687045226742, 2.1369938048939527, 3.730913391951158, 10.929856967963905, 8.301187183717643, -4.874133827873075, 0.7918650606624789, -8.520661635525103, -7.732342981599732, -6.494750491582618, -2.458749173402162, 3.573788336699224, 2.784339193089742, -1.6479372032388944, -0.35120747879544256]
Line 1,370 ⟶ 1,487:
From Javascript.
 
<langsyntaxhighlight lang="javascript">/* Geometric Algebra, in Jsih */
 
var GA = function () {
Line 1,496 ⟶ 1,613:
GA.mul(x, x) ==> [ 1.659737254471485, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
=!EXPECTEND!=
*/</langsyntaxhighlight>
 
{{out}}
Line 1,504 ⟶ 1,621:
=={{header|Julia}}==
{{trans|Kotlin}}
<langsyntaxhighlight lang="julia">using GeometryTypes
import Base.*
 
Line 1,563 ⟶ 1,680:
 
testcliffordvector()
</langsyntaxhighlight>{{out}}
<pre>
e(i) * e(j) are orthonormal for i, j ϵ [0, 4]: true
Line 1,574 ⟶ 1,691:
=={{header|Kotlin}}==
{{trans|Go}}
<langsyntaxhighlight lang="scala">fun bitCount(i: Int): Int {
var j = i
j -= ((j shr 1) and 0x55555555)
Line 1,723 ⟶ 1,840:
// x^2 is real
println(x * x)
}</langsyntaxhighlight>
{{out}}
<pre>(-6.38113123172589, -6.025395204580336, 0.5762054454373319, -2.224611121553874, -0.03467815839340305, -0.6665488550665257, -3.012105902847624, 0.7315782457554153, -4.183528079943369, -1.8391037440709876, -0.137654892093293, 0.10852885457965271, -6.021317788342983, -5.486453322362711, -3.524908677069778, -1.030729377561671, -6.858194536947578, -8.724962937014816, 0.4660400096706247, -1.6434599565678671, 4.212637141194194, 2.916899539720754, -1.365566480297562, 1.898991559248674, -2.5943503153384517, -0.7167616808942235, 1.2152416665362584, 2.9936787524618067, -5.394453145898911, -4.180356766796923, -6.622391097517418, -4.249450373116712)
Line 1,736 ⟶ 1,853:
(2.6501903002573224, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0)</pre>
 
=={{header|PhixNim}}==
{{trans|Go}}
<syntaxhighlight lang="nim">import bitops, random, sequtils, strutils
<lang Phix>function bitCount(integer i)
return sum(sq_eq(sprintf("%b",i),'1')) -- (idea cribbed from Python)
end function
function reorderingSign(integer i, j)
i = floor(i/2)
integer tot := 0
while i!=0 do
tot += bitCount(and_bits(i,j))
i = floor(i/2)
end while
return iff(and_bits(tot,1)==0 ? 1 : -1)
end function
function add(sequence a, b)
return sq_add(a,b)
end function
 
type Vector = seq[float]
function mul(sequence a, b)
sequence result = repeat(0,32)
for i=1 to length(a) do
if a[i]!=0 then
for j=1 to length(b) do
if b[j]!=0 then
atom s := reorderingSign(i-1, j-1) * a[i] * b[j]
integer k = xor_bits(i-1,j-1)+1
result[k] += s
end if
end for
end if
end for
return result
end function
function cdot(sequence a, b)
return mul({0.5}, add(mul(a, b), mul(b, a)))
end function
function e(integer n)
if n>4 then crash("n must be less than 5") end if
sequence result = repeat(0,32)
result[power(2,n)+1] = 1.0
return result
end function
--function neg(sequence x) -- (not actually used here)
-- return mul({-1}, x)
--end function
function randomVector()
sequence result = repeat(0,32)
for i=0 to 4 do
result = add(result, mul({rnd()}, e(i)))
end for
return result
end function
function randomMultiVector()
sequence result = repeat(0, 32)
for i=1 to 32 do
result[i] = rnd()
end for
return result
end function
 
func reorderingSign(i, j: int): float =
for i=0 to 4 do
var i for j=0 toi 4shr do1
var sum = 0
if i < j then
while i != 0:
if cdot(e(i), e(j))[1] != 0 then
sum += countSetBits(i and j)
crash("Unexpected non-null scalar product.")
i = i shr end if1
result = if (sum and elsif i1) == j0: 1 else: then-1
if cdot(e(i), e(j))[1] == 0 then
crash("Unexpected null scalar product.")
end if
end if
end for
end for
sequence a := randomMultiVector(),
b := randomMultiVector(),
c := randomMultiVector(),
x := randomVector(),
xsq = mul(x, x)
 
func e(n: Natural): Vector =
procedure test(string txt, sequence a, b)
result.setLen(32)
-- bool eq = (a==b) -- no!
assert n < 5, "index must be less than 5; got $#.".format(n)
bool eq = (sprint(a)==sprint(b)) -- ok!
result[1 shl n] = 1
printf(1,"%-20s: %s\n",{txt,iff(eq?"true","false")})
end procedure
test("(ab)c == a(bc)",mul(mul(a, b), c),
mul(a, mul(b, c)))
 
func `+`(a, b: Vector): Vector =
test("a(b + c) == ab + ac",mul(a, add(b, c)),
result.setLen(32)
add(mul(a, b), mul(a, c)))
for i in 0..b.high:
result[i] = a[i] + b[i]
test("(a + b)c == ac + bc",mul(add(a, b), c),
 
add(mul(a, c), mul(b, c)))
func `*`(a, b: Vector): Vector =
result.setLen(32)
test("x^2 is real",xsq,xsq[1]&repeat(0,31))</lang>
for i in 0..a.high:
if a[i] != 0:
for j in 0..b.high:
if b[j] != 0:
let s = reorderingSign(i, j) * a[i] * b[j]
let k = i xor j
result[k] += s
 
func dot(a, b: Vector): Vector =
(a * b + b * a) * @[0.5]
 
proc randomVector(): Vector =
result.setLen(32)
for i in 0..4:
result = result + @[rand(1.0)] * e(i)
 
proc randomMultiVector(): Vector =
newSeqWith(32, rand(1.0))
 
 
when isMainModule:
 
randomize()
for i in 0..4:
for j in 0..4:
if i < j:
if dot(e(i), e(j))[0] != 0:
raise newException(ValueError, "Unexpected non-null scalar product.")
elif i == j:
if dot(e(i), e(j))[0] == 0:
raise newException(ValueError, "Unexpected null scalar product.")
 
let a = randomMultiVector()
let b = randomMultiVector()
let c = randomMultiVector()
let x = randomVector()
 
# (ab)c == a(bc).
echo (a * b) * c
echo a * (b * c)
echo()
 
# a(b + c) == ab + ac.
echo a * (b + c)
echo a * b + a * c
echo()
 
# (a + b)c == ac + bc.
echo (a + b) * c
echo a * c + b * c
echo()
 
# x² is real.
echo x * x</syntaxhighlight>
 
{{out}}
<pre>@[-9.297288337196365, -13.59127999209494, 0.8722218109740326, 1.226935672314977, 7.508102247367465, 4.724948516329687, -5.033061024827017, -1.610503728288931, -3.33431529299565, 0.3532979194154671, 4.301275797990844, 0.515295984242726, 4.687736789474281, 2.172013218653572, 1.231492215423554, 0.3536950472866263, -2.327900412362799, -9.527999065273885, -1.555602751234329, 5.382767377500711, 6.267283581472086, 2.76910363753004, -2.301420318996988, 3.652383163769268, 1.752589228395532, 5.939099169023176, 4.479735695808257, 0.01446097776030125, -2.363384273037976, -5.720151847201447, -0.9397636030508162, -6.25507506195876]
@[-9.297288337196365, -13.59127999209493, 0.872221810974033, 1.226935672314978, 7.508102247367463, 4.72494851632969, -5.033061024827017, -1.610503728288931, -3.334315292995649, 0.3532979194154663, 4.301275797990842, 0.5152959842427232, 4.687736789474281, 2.172013218653572, 1.231492215423554, 0.3536950472866283, -2.327900412362798, -9.527999065273882, -1.55560275123433, 5.382767377500712, 6.267283581472084, 2.76910363753004, -2.301420318996988, 3.652383163769271, 1.752589228395533, 5.939099169023176, 4.47973569580826, 0.01446097776030148, -2.363384273037971, -5.720151847201445, -0.9397636030508175, -6.255075061958758]
 
@[-2.586487554821921, -2.653533704207625, 2.766021230656747, 2.036067471647896, 3.190493529679435, 2.42809912090021, 0.6900349473229486, 2.878934763823856, -3.935215841511595, -0.7288825987300381, 6.463778612248242, 4.417536841852129, 0.636912176867748, 4.413110019589562, 2.623393232840747, 1.608010580836939, -0.5328933745526506, -3.058074932298209, 2.178373565254037, 2.495618455562951, 4.609639873172126, 2.906729883514136, -0.934662696267724, 0.1369174733899857, 0.7572410282960323, 2.600596775217479, 4.079925278716743, 2.378076954647832, -1.529999013986847, 4.451662845891456, 0.07968415835836305, 0.7302442935297417]
@[-2.586487554821921, -2.653533704207625, 2.766021230656746, 2.036067471647896, 3.190493529679435, 2.42809912090021, 0.6900349473229492, 2.878934763823857, -3.935215841511596, -0.7288825987300391, 6.463778612248241, 4.417536841852128, 0.6369121768677473, 4.413110019589563, 2.623393232840748, 1.60801058083694, -0.5328933745526511, -3.058074932298209, 2.178373565254037, 2.495618455562951, 4.609639873172125, 2.906729883514135, -0.9346626962677241, 0.1369174733899854, 0.7572410282960332, 2.600596775217479, 4.079925278716742, 2.378076954647831, -1.529999013986847, 4.451662845891456, 0.0796841583583624, 0.7302442935297415]
 
@[-4.043970500041602, -6.87480031917386, 2.141017248170762, 0.3993395131802852, 0.8031440447491957, 3.401648770759057, 1.607243807621857, 3.522447744273161, -1.991055803046583, -0.7625625003549232, 6.536037328177198, 3.860062375500871, 2.237849358894385, 4.651754451010404, 8.300896571599077, 4.846096568587825, -2.0442907200416, -4.305082016141705, -0.9716874582456112, 0.214856705219781, 3.6445786747822, 2.050775132011032, -2.303468928921437, -1.111677463505033, 2.776551776801528, 1.829715078662076, 4.565478899003429, 1.874485695211426, -2.682597285575913, 1.056667802512815, 4.075588220758377, 1.609677009616234]
@[-4.043970500041601, -6.874800319173863, 2.141017248170761, 0.3993395131802844, 0.8031440447491961, 3.401648770759058, 1.607243807621859, 3.522447744273161, -1.991055803046583, -0.7625625003549237, 6.536037328177197, 3.860062375500871, 2.237849358894385, 4.651754451010405, 8.300896571599079, 4.846096568587828, -2.044290720041601, -4.305082016141704, -0.9716874582456119, 0.2148567052197807, 3.6445786747822, 2.050775132011031, -2.303468928921436, -1.111677463505034, 2.776551776801528, 1.829715078662075, 4.565478899003429, 1.874485695211426, -2.682597285575913, 1.056667802512815, 4.075588220758375, 1.609677009616233]
 
@[2.298735784397904, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0]</pre>
 
=={{header|Phix}}==
{{trans|Go}}
<!--<syntaxhighlight lang="phix">(phixonline)-->
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">bitCount</span><span style="color: #0000FF;">(</span><span style="color: #004080;">integer</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">return</span> <span style="color: #7060A8;">sum</span><span style="color: #0000FF;">(</span><span style="color: #7060A8;">sq_eq</span><span style="color: #0000FF;">(</span><span style="color: #7060A8;">sprintf</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"%b"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">i</span><span style="color: #0000FF;">),</span><span style="color: #008000;">'1'</span><span style="color: #0000FF;">))</span> <span style="color: #000080;font-style:italic;">-- (idea cribbed from Python)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">reorderingSign</span><span style="color: #0000FF;">(</span><span style="color: #004080;">integer</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">j</span><span style="color: #0000FF;">)</span>
<span style="color: #000000;">i</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">floor</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">/</span><span style="color: #000000;">2</span><span style="color: #0000FF;">)</span>
<span style="color: #004080;">integer</span> <span style="color: #000000;">tot</span> <span style="color: #0000FF;">:=</span> <span style="color: #000000;">0</span>
<span style="color: #008080;">while</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">!=</span><span style="color: #000000;">0</span> <span style="color: #008080;">do</span>
<span style="color: #000000;">tot</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">bitCount</span><span style="color: #0000FF;">(</span><span style="color: #7060A8;">and_bits</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">,</span><span style="color: #000000;">j</span><span style="color: #0000FF;">))</span>
<span style="color: #000000;">i</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">floor</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">/</span><span style="color: #000000;">2</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">while</span>
<span style="color: #008080;">return</span> <span style="color: #008080;">iff</span><span style="color: #0000FF;">(</span><span style="color: #7060A8;">and_bits</span><span style="color: #0000FF;">(</span><span style="color: #000000;">tot</span><span style="color: #0000FF;">,</span><span style="color: #000000;">1</span><span style="color: #0000FF;">)==</span><span style="color: #000000;">0</span> <span style="color: #0000FF;">?</span> <span style="color: #000000;">1</span> <span style="color: #0000FF;">:</span> <span style="color: #0000FF;">-</span><span style="color: #000000;">1</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #004080;">sequence</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">return</span> <span style="color: #7060A8;">sq_add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span><span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #004080;">sequence</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
<span style="color: #004080;">sequence</span> <span style="color: #000000;">result</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">repeat</span><span style="color: #0000FF;">(</span><span style="color: #000000;">0</span><span style="color: #0000FF;">,</span><span style="color: #000000;">32</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">do</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">]!=</span><span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">j</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">b</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">do</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">[</span><span style="color: #000000;">j</span><span style="color: #0000FF;">]!=</span><span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
<span style="color: #004080;">atom</span> <span style="color: #000000;">s</span> <span style="color: #0000FF;">:=</span> <span style="color: #000000;">reorderingSign</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">-</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">j</span><span style="color: #0000FF;">-</span><span style="color: #000000;">1</span><span style="color: #0000FF;">)</span> <span style="color: #0000FF;">*</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">*</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">[</span><span style="color: #000000;">j</span><span style="color: #0000FF;">]</span>
<span style="color: #004080;">integer</span> <span style="color: #000000;">k</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">xor_bits</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">-</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #000000;">j</span><span style="color: #0000FF;">-</span><span style="color: #000000;">1</span><span style="color: #0000FF;">)+</span><span style="color: #000000;">1</span>
<span style="color: #000000;">result</span><span style="color: #0000FF;">[</span><span style="color: #000000;">k</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">s</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #008080;">return</span> <span style="color: #000000;">result</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">cdot</span><span style="color: #0000FF;">(</span><span style="color: #004080;">sequence</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">return</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">({</span><span style="color: #000000;">0.5</span><span style="color: #0000FF;">},</span> <span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">b</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">)))</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">e</span><span style="color: #0000FF;">(</span><span style="color: #004080;">integer</span> <span style="color: #000000;">n</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">n</span><span style="color: #0000FF;">></span><span style="color: #000000;">4</span> <span style="color: #008080;">then</span> <span style="color: #7060A8;">crash</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"n must be less than 5"</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #004080;">sequence</span> <span style="color: #000000;">result</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">repeat</span><span style="color: #0000FF;">(</span><span style="color: #000000;">0</span><span style="color: #0000FF;">,</span><span style="color: #000000;">32</span><span style="color: #0000FF;">)</span>
<span style="color: #000000;">result</span><span style="color: #0000FF;">[</span><span style="color: #7060A8;">power</span><span style="color: #0000FF;">(</span><span style="color: #000000;">2</span><span style="color: #0000FF;">,</span><span style="color: #000000;">n</span><span style="color: #0000FF;">)+</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">1.0</span>
<span style="color: #008080;">return</span> <span style="color: #000000;">result</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #000080;font-style:italic;">--function neg(sequence x) -- (not actually used here)
-- return mul({-1}, x)
--end function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">randomVector</span><span style="color: #0000FF;">()</span>
<span style="color: #004080;">sequence</span> <span style="color: #000000;">result</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">repeat</span><span style="color: #0000FF;">(</span><span style="color: #000000;">0</span><span style="color: #0000FF;">,</span><span style="color: #000000;">32</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span> <span style="color: #008080;">to</span> <span style="color: #000000;">4</span> <span style="color: #008080;">do</span>
<span style="color: #000000;">result</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">result</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">({</span><span style="color: #7060A8;">rnd</span><span style="color: #0000FF;">()},</span> <span style="color: #000000;">e</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">)))</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #008080;">return</span> <span style="color: #000000;">result</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">function</span> <span style="color: #000000;">randomMultiVector</span><span style="color: #0000FF;">()</span>
<span style="color: #004080;">sequence</span> <span style="color: #000000;">result</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">repeat</span><span style="color: #0000FF;">(</span><span style="color: #000000;">0</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">32</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #000000;">32</span> <span style="color: #008080;">do</span>
<span style="color: #000000;">result</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">rnd</span><span style="color: #0000FF;">()</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #008080;">return</span> <span style="color: #000000;">result</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">function</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span> <span style="color: #008080;">to</span> <span style="color: #000000;">4</span> <span style="color: #008080;">do</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">j</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span> <span style="color: #008080;">to</span> <span style="color: #000000;">4</span> <span style="color: #008080;">do</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">i</span> <span style="color: #0000FF;"><</span> <span style="color: #000000;">j</span> <span style="color: #008080;">then</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">cdot</span><span style="color: #0000FF;">(</span><span style="color: #000000;">e</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">e</span><span style="color: #0000FF;">(</span><span style="color: #000000;">j</span><span style="color: #0000FF;">))[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">!=</span> <span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
<span style="color: #7060A8;">crash</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"Unexpected non-null scalar product."</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">elsif</span> <span style="color: #000000;">i</span> <span style="color: #0000FF;">==</span> <span style="color: #000000;">j</span> <span style="color: #008080;">then</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">cdot</span><span style="color: #0000FF;">(</span><span style="color: #000000;">e</span><span style="color: #0000FF;">(</span><span style="color: #000000;">i</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">e</span><span style="color: #0000FF;">(</span><span style="color: #000000;">j</span><span style="color: #0000FF;">))[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">==</span> <span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
<span style="color: #7060A8;">crash</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"Unexpected null scalar product."</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #004080;">sequence</span> <span style="color: #000000;">a</span> <span style="color: #0000FF;">:=</span> <span style="color: #000000;">randomMultiVector</span><span style="color: #0000FF;">(),</span>
<span style="color: #000000;">b</span> <span style="color: #0000FF;">:=</span> <span style="color: #000000;">randomMultiVector</span><span style="color: #0000FF;">(),</span>
<span style="color: #000000;">c</span> <span style="color: #0000FF;">:=</span> <span style="color: #000000;">randomMultiVector</span><span style="color: #0000FF;">(),</span>
<span style="color: #000000;">x</span> <span style="color: #0000FF;">:=</span> <span style="color: #000000;">randomVector</span><span style="color: #0000FF;">(),</span>
<span style="color: #000000;">xsq</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">x</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">x</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">procedure</span> <span style="color: #000000;">test</span><span style="color: #0000FF;">(</span><span style="color: #004080;">string</span> <span style="color: #000000;">txt</span><span style="color: #0000FF;">,</span> <span style="color: #004080;">sequence</span> <span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">)</span>
<span style="color: #000080;font-style:italic;">-- bool eq = (a==b) -- no!</span>
<span style="color: #004080;">bool</span> <span style="color: #000000;">eq</span> <span style="color: #0000FF;">=</span> <span style="color: #0000FF;">(</span><span style="color: #7060A8;">sprint</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">)==</span><span style="color: #7060A8;">sprint</span><span style="color: #0000FF;">(</span><span style="color: #000000;">b</span><span style="color: #0000FF;">))</span> <span style="color: #000080;font-style:italic;">-- ok!</span>
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"%-20s: %s\n"</span><span style="color: #0000FF;">,{</span><span style="color: #000000;">txt</span><span style="color: #0000FF;">,</span><span style="color: #008080;">iff</span><span style="color: #0000FF;">(</span><span style="color: #000000;">eq</span><span style="color: #0000FF;">?</span><span style="color: #008000;">"true"</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"false"</span><span style="color: #0000FF;">)})</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">procedure</span>
<span style="color: #000000;">test</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"(ab)c == a(bc)"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">),</span>
<span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">b</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">)))</span>
<span style="color: #000000;">test</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"a(b + c) == ab + ac"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">b</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">)),</span>
<span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">)))</span>
<span style="color: #000000;">test</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"(a + b)c == ac + bc"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">b</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">),</span>
<span style="color: #000000;">add</span><span style="color: #0000FF;">(</span><span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">a</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">mul</span><span style="color: #0000FF;">(</span><span style="color: #000000;">b</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">c</span><span style="color: #0000FF;">)))</span>
<span style="color: #000000;">test</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"x^2 is real"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">xsq</span><span style="color: #0000FF;">,</span><span style="color: #000000;">xsq</span><span style="color: #0000FF;">[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]&</span><span style="color: #7060A8;">repeat</span><span style="color: #0000FF;">(</span><span style="color: #000000;">0</span><span style="color: #0000FF;">,</span><span style="color: #000000;">31</span><span style="color: #0000FF;">))</span>
<!--</syntaxhighlight>-->
{{out}}
Note the comparison of string representations of floats, rather than the floats themselves. That effectively ensures they
Line 1,851 ⟶ 2,064:
=={{header|Python}}==
{{trans|D}}
<langsyntaxhighlight lang="python">import copy, random
 
def bitcount(n):
Line 1,958 ⟶ 2,171:
print x * x
 
main()</langsyntaxhighlight>
{{out}}
<pre>[2.646777769717816, -5.480686120935684, -8.183342078006843, -9.178717618666656, -0.21247781959240397, -3.1560121872423172, -14.210376795019405, -7.975576839132462, -2.963314079857538, -8.128489630952732, 8.84291288803876, 6.849688422048398, -3.948403894153645, -6.3295864734054295, 0.858339386946704, 0.04073276768257372, -0.8170168057484614, -5.987310468330181, -5.089567141509365, -6.5916164371098205, 1.066652018944462, -0.7553724661211869, -16.61957782752131, -10.74332838047719, -0.22326945346944393, -5.502857138805277, 11.833089760883906, 11.020055749901102, -3.7471254230186233, -3.5483496341413763, 7.788213699886802, 5.385261642366723]
Line 1,976 ⟶ 2,189:
Here we write a simplified version of the [https://github.com/grondilu/clifford Clifford] module. It is very general as it is of infinite dimension and also contains an anti-euclidean basis @ē in addition to the euclidean basis @e.
 
<syntaxhighlight lang="raku" perl6line>unit class MultiVector; is Mix {
subset UIntHashVector of MixHash::?CLASS is export where *.keysgrades.all ~~== UInt1;
has UIntHash $.blades;
method narrow { $!blades.keys.any > 0 ?? self !! ($!blades{0} // 0) }
 
multi method new(Realnarrow $x){ returnsself.keys.any MultiVector> {0 ?? self.new: !! (self{0} =>// $x0).MixHash }
multi method new(UIntHash $blades) returns MultiVectorgrades { self.newkeys.map: :$blades*.base(2).comb.sum }
 
multi method new(StrReal $x) wherereturns /^^e(\d+)$$/)::?CLASS { self.new-from-pairs: (10 +<=> (2*$0)).MixHashx }
multi method new(Str $ where /^^ēe(\d+)$$/) { self.new-from-pairs: (1 +< (2*$0)) +=> 1)).MixHash }
 
our @e is export = map { MultiVector::?CLASS.new: "e$_" }, ^Inf;
our @ē is export = map { MultiVector.new: "ē$_" }, ^Inf;
 
my sub order(UInt:D $i is copy, UInt:D $j) {
(state %){$i}{$j} //= do {
my $n = 0;
repeat {
$i +>= 1;
$n += [+] ($i +& $j).polymod(2 xx *);
} until $i == 0;
$n +& 1 ?? -1 !! 1;
}
}
 
multi sub infix:<+·>(MultiVectorVector $Ax, MultiVectorVector $By) returns MultiVectorReal is export { (($x*$y + $y*$x)/2){0} }
return MultiVector.new: ($A.blades.pairs, |$B.blades.pairs).MixHash;
multi infix:<+>(::?CLASS $A, ::?CLASS $B) returns ::?CLASS is export {
}
return ::?CLASS.new-from-pairs: |$A.pairs, |$B.pairs;
multi infix:<+>(Real $s, MultiVector $B) returns MultiVector is export {
}
return MultiVector.new: (0 => $s, |$B.blades.pairs).MixHash;
multi infix:<+>(Real $s, ::?CLASS $B) returns ::?CLASS is export {
}
samewith $B.new($s), $B
multi infix:<+>(MultiVector $A, Real $s) returns MultiVector is export { $s + $A }
}
multi infix:<+>(::?CLASS $A, Real $s) returns ::?CLASS is export {
samewith $s, $A
}
 
multi infix:<*>(MultiVector::?CLASS $, 0) is export { 0 }
multi infix:<*>(MultiVector::?CLASS $A, 1) returns MultiVector::?CLASS is export { $A }
multi infix:<*>(MultiVector::?CLASS $A, Real $s) returns MultiVector::?CLASS is export {
MultiVector::?CLASS.new-from-pairs: $A.blades.pairs.map({Pair.new: .key, $s*.value}).MixHash
}
multi infix:<*>(MultiVector::?CLASS $A, MultiVector::?CLASS $B) returns MultiVector::?CLASS is export {
::?CLASS.new-from-pairs: gather
MultiVector.new: do for $A.blades -> $a {
|do for $BA.bladespairs -> $ba {
for ($aB.keypairs +^-> $b.key) => [*]{
take ($a.key +^ $b.key) => [*]
$a.value, $b.value,
order($a.key, $b.key),
Line 2,025 ⟶ 2,240:
)
}
}.MixHash
}
multi infix:<**>(MultiVector::?CLASS $ , 0) returns MultiVector::?CLASS is export { MultiVector::?CLASS.new: (0 => 1).Mix }
multi infix:<**>(MultiVector::?CLASS $A, 1) returns MultiVector::?CLASS is export { $A }
multi infix:<**>(MultiVector::?CLASS $A, 2) returns MultiVector::?CLASS is export { $A * $A }
multi infix:<**>(MultiVector::?CLASS $A, UInt $n where $n %% 2) returns MultiVector::?CLASS is export { ($A ** ($n div 2)) ** 2 }
multi infix:<**>(MultiVector::?CLASS $A, UInt $n) returns MultiVector::?CLASS is export { $A * ($A ** ($n div 2)) ** 2 }
 
multi infix:<*>(Real $s, MultiVector::?CLASS $A) returns MultiVector::?CLASS is export { $A * $s }
multi infix:</>(MultiVector::?CLASS $A, Real $s) returns MultiVector::?CLASS is export { $A * (1/$s) }
multi prefix:<->(MultiVector::?CLASS $A) returns MultiVector::?CLASS is export { return -1 * $A }
multi infix:<->(MultiVector::?CLASS $A, MultiVector::?CLASS $B) returns MultiVector::?CLASS is export { $A + -$B }
multi infix:<->(MultiVector::?CLASS $A, Real $s) returns MultiVector::?CLASS is export { $A + -$s }
multi infix:<->(Real $s, MultiVector::?CLASS $A) returns MultiVector::?CLASS is export { $s + -$A }
 
multi infix:<==>(MultiVector::?CLASS $A, MultiVector $B0) returns Bool is export { $A - $B.elems == 0 }
multi infix:<==>(Real::?CLASS $xA, MultiVector::?CLASS $AB) returns Bool is export { samewith $A ==- $xB, 0 }
multi infix:<==>(MultiVectorReal $Ax, Real::?CLASS $xA) returns Bool is export { samewith $A, $x }
multi infix:<==>(::?CLASS $A, Real $x) returns Bool is export { samewith $A, $A.new($x); }
my $narrowed = $A.narrow;
 
$narrowed ~~ Real and $narrowed == $x;
sub random is export {
[+] map {
::?CLASS.new-from-pairs: $_ => rand.round(.01)
}, ^32;
}
}
 
Line 2,051 ⟶ 2,271:
#########################################
 
import MultiVector;
use Test;
constant N = 10;
plan 29;
plan 5;
subtest "Orthonormality", {
sub infix:<cdot>($x, $y) { ($x*$y + $y*$x)/2 }
for ^N X ^N -> ($i, $j) {
for ^5 X ^5 -> ($i, $j) {
my $s = $i == $j ?? 1 !! 0;
ok @e[$i] cdot ·@e[$j] == $s, "e$i cdot ·e$j = $s";
}
sub random {
[+] map {
MultiVector.new:
:blades(($_ => rand.round(.01)).MixHash)
}, ^32;
}
Line 2,075 ⟶ 2,291:
my @coeff = (.5 - rand) xx 5;
my $v = [+] @coeff Z* @e[^5];
ok ($v**2).narrow ~~ Real, 'contraction';</langsyntaxhighlight>
 
=={{header|Visual Basic .NET}}==
{{trans|C#}}
<langsyntaxhighlight lang="vbnet">Option Strict On
 
Imports System.Text
Line 2,270 ⟶ 2,486:
End Sub
 
End Module</langsyntaxhighlight>
{{out}}
<pre>[0.574263754349833, -1.04033308353824, -0.776121961159351, 2.00792496222078, 3.16921091358851, 6.73557610270275, -13.4327886840529, -7.74195172209513, -7.21674283588092, -5.86045645950882, 2.22312083899981, 1.32215440847646, -6.14796858424355, -6.31067579900569, -8.24016821785677, -7.13138966213629, 1.70037903072841, -1.61670055512076, -1.53920826677554, 0.0830404550813257, 3.93618132588852, 7.40029585163889, -6.36594388310886, 2.14605789872596, -12.3353817163416, -9.51720072572794, 4.57164353732716, 3.11601890765627, -3.45821025466289, -4.2333151576991, -5.88080545860622, -6.53549242641427]
Line 2,282 ⟶ 2,498:
 
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]</pre>
 
=={{header|Wren}}==
{{trans|Kotlin}}
<syntaxhighlight lang="wren">import "random" for Random
 
var bitCount = Fn.new { |i|
i = i - ((i >> 1) & 0x55555555)
i = (i & 0x33333333) + ((i >> 2) & 0x33333333)
i = (i + (i >> 4)) & 0x0f0f0f0f
i = i + (i >> 8)
i = i + (i >> 16)
return i & 0x0000003F
}
 
var ReorderingSign = Fn.new { |i, j|
var k = i >> 1
var sum = 0
while (k != 0) {
sum = sum + bitCount.call(k & j)
k = k >> 1
}
return (sum & 1 == 0) ? 1 : -1
}
 
class Vector {
construct new(dims) {
_dims = dims
}
 
dims { _dims }
 
dot(rhs) { (this * rhs + rhs * this) * 0.5 }
 
- { this * -1 }
 
+(rhs) {
var result = List.filled(32, 0)
for (i in 0..._dims.count) result[i] = _dims[i]
for (i in 0...rhs.dims.count) result[i] = result[i] + rhs[i]
return Vector.new(result)
}
 
*(rhs) {
if (rhs is Vector) {
var result = List.filled(32, 0)
for (i in 0..._dims.count) {
if (_dims[i] != 0) {
for (j in 0...rhs.dims.count) {
if (rhs[j] != 0) {
var s = ReorderingSign.call(i, j) * _dims[i] * rhs[j]
var k = i ^ j
result[k] = result[k] + s
}
}
}
}
return Vector.new(result)
} else if (rhs is Num) {
var result = _dims.toList
for (i in 0..4) dims[i] = dims[i] * rhs
return Vector.new(result)
} else {
Fiber.abort("rhs must either be a Vector or a number")
}
}
 
[index] { _dims[index] }
 
[index]=(value) { _dims[index] = value }
 
toString { "(" + _dims.join(", ") + ")" }
}
 
var e = Fn.new { |n|
if (n > 4) Fiber.abort("n must be less than 5")
var result = Vector.new(List.filled(32, 0))
result[1 << n] = 1
return result
}
 
var rand = Random.new()
 
var randomVector = Fn.new {
var result = Vector.new(List.filled(32, 0))
for (i in 0..4) {
result = result + Vector.new([rand.float()]) * e.call(i)
}
return result
}
 
var randomMultiVector = Fn.new {
var result = Vector.new(List.filled(32, 0))
for (i in 0..31) result[i] = rand.float()
return result
}
 
for (i in 0..4) {
for (j in 0..4) {
if (i < j) {
if (e.call(i).dot(e.call(j))[0] != 0) {
System.print("Unexpected non-null scalar product.")
return
} else if (i == j) {
if (e.call(i).dot(e.call(j))[0] == 0) {
System.print("Unexpected null scalar product.")
}
}
}
}
}
 
var a = randomMultiVector.call()
var b = randomMultiVector.call()
var c = randomMultiVector.call()
var x = randomVector.call()
 
// (ab)c == a(bc)
System.print((a * b) * c)
System.print(a * (b * c))
System.print()
 
// a(b+c) == ab + ac
System.print(a * (b + c))
System.print(a * b + a * c)
System.print()
 
// (a+b)c == ac + bc
System.print((a + b) * c)
System.print(a * c + b * c)
System.print()
 
// x^2 is real
System.print(x * x)</syntaxhighlight>
 
{{out}}
<pre>
(-6.1279343499972, -12.172471890613, -0.43596654360835, -9.4733600789769, 7.7468131011607, -1.0197449680744, -8.3386053167094, -4.514411938465, -0.85417113341489, 5.814264590591, 4.7534441812565, 3.6983892972325, -1.9487633151975, 1.0081516771802, 3.793528331478, -0.71739309800609, -5.0930834896765, -10.389798935116, -0.21991874396827, -9.2747185990727, 2.4902263109011, -1.217404792573, -7.5648404539069, -5.1713187775853, -4.9297458419615, -2.5365579590808, 5.6741886500532, -5.3820954955896, 0.84309276379896, -0.83865672543758, -6.6627947524069, -6.5068089919902)
(-6.1279343499972, -12.172471890613, -0.43596654360835, -9.4733600789769, 7.7468131011607, -1.0197449680744, -8.3386053167094, -4.514411938465, -0.85417113341489, 5.814264590591, 4.7534441812565, 3.6983892972325, -1.9487633151975, 1.0081516771802, 3.793528331478, -0.71739309800609, -5.0930834896765, -10.389798935116, -0.21991874396827, -9.2747185990727, 2.4902263109011, -1.217404792573, -7.5648404539069, -5.1713187775853, -4.9297458419615, -2.5365579590808, 5.6741886500532, -5.3820954955896, 0.84309276379896, -0.83865672543757, -6.6627947524069, -6.5068089919902)
 
(-4.5670205884692, -5.406285276749, 0.20435321499717, -4.7297569961965, 3.1536400277791, 4.3228858614581, -2.648422809333, -1.1833380429978, -1.7564258015137, 3.3290322042955, 4.1877600392827, 5.7622202559563, -2.6969120760046, 1.6040264499734, 1.7140507294369, 3.3982272822008, -2.7897066050195, -2.800819409065, 2.2770258183891, -1.3567979021271, 2.4379457462826, 4.9315720878673, -1.8523904994524, 0.57286280886659, 0.78942446076958, 3.2321401010964, 2.7052700803603, 4.1875465627791, -1.9573353620592, 3.042768958901, 0.55331226143665, 3.4813647018728)
(-4.5670205884692, -5.406285276749, 0.20435321499716, -4.7297569961965, 3.1536400277791, 4.3228858614581, -2.648422809333, -1.1833380429978, -1.7564258015137, 3.3290322042955, 4.1877600392827, 5.7622202559563, -2.6969120760046, 1.6040264499734, 1.7140507294369, 3.3982272822008, -2.7897066050195, -2.800819409065, 2.2770258183891, -1.3567979021271, 2.4379457462826, 4.9315720878673, -1.8523904994524, 0.57286280886659, 0.78942446076958, 3.2321401010964, 2.7052700803603, 4.1875465627791, -1.9573353620592, 3.042768958901, 0.55331226143665, 3.4813647018728)
 
(-6.4947965411446, -7.5334457985612, -0.48336700984287, -2.6235798111818, 3.6406622303652, 3.6398682775911, -1.8835092927705, -4.0165723310492, 1.6332945757193, 5.2056992102457, 4.202039318349, 7.3784879794787, -2.4843920053947, -0.47893361628939, 1.1220802570638, 2.693375877108, -1.278951846965, -2.5982492127516, 0.85382005828955, -0.077629574978695, 5.211354827205, 6.5199779982554, 0.85742615796087, -0.062281151554669, -1.4540738133743, 1.6710486134883, 3.8433969630048, 6.4484021393956, 2.8236029776283, 2.9302728085944, 1.3066828942527, 3.7490534064109)
(-6.4947965411446, -7.5334457985612, -0.48336700984287, -2.6235798111818, 3.6406622303652, 3.6398682775912, -1.8835092927705, -4.0165723310492, 1.6332945757193, 5.2056992102457, 4.202039318349, 7.3784879794787, -2.4843920053947, -0.47893361628939, 1.1220802570638, 2.693375877108, -1.278951846965, -2.5982492127516, 0.85382005828955, -0.077629574978696, 5.211354827205, 6.5199779982554, 0.85742615796087, -0.062281151554668, -1.4540738133743, 1.6710486134883, 3.8433969630048, 6.4484021393956, 2.8236029776283, 2.9302728085944, 1.3066828942527, 3.7490534064109)
 
(0.96552083436649, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0)
</pre>
2,123

edits