Radice quadrata del quaternione


11

sfondo

Quaternion è un sistema numerico che estende numeri complessi. Un quaternione ha la seguente forma

a+bi+cj+dk

dove a,b,c,d sono numeri reali e i,j,k sono tre unità quaternione fondamentali . Le unità hanno le seguenti proprietà:

i2=j2=k2=1
ij=k,jk=i,ki=j
ji=k,kj=i,ik=j

Si noti che la moltiplicazione del quaternione non è commutativa .

Compito

Dato un quaternione non reale , calcola almeno una delle sue radici quadrate.

Come?

Secondo questa risposta Math.SE , possiamo esprimere qualsiasi quaternione non reale nella seguente forma:

q=a+bu

dove a,b sono numeri reali e u è il vettore unitario immaginario nella forma xi+yj+zk con x2+y2+z2=1 . Qualunque u ha la proprietà u2=1 , quindi può essere vista come unità immaginaria.

Quindi il quadrato di q è simile al seguente:

q2=(a2b2)+2abu

Inversamente, dato un quaternione q=x+yu , possiamo trovare la radice quadrata di q risolvendo le seguenti equazioni

x=a2b2,y=2ab

che è identico al processo di ricerca della radice quadrata di un numero complesso.

Si noti che un numero reale negativo ha infinitamente molte radici quadrate di quaternione, ma un quaternione non reale ha solo due radici quadrate .

Ingresso e uscita

L'input è un quaternione non reale. Puoi prenderlo come quattro numeri reali (in virgola mobile), in qualsiasi ordine e struttura di tua scelta. Non reale significa che almeno uno di b,c,d è diverso da zero.

L'output è uno o due quaternioni che, al quadrato, sono uguali all'input.

Casi test

   Input (a, b, c, d)  =>  Output (a, b, c, d) rounded to 6 digits

 0.0,  1.0,  0.0,  0.0 =>  0.707107,  0.707107,  0.000000,  0.000000
 1.0,  1.0,  0.0,  0.0 =>  1.098684,  0.455090,  0.000000,  0.000000
 1.0, -1.0,  1.0,  0.0 =>  1.168771, -0.427800,  0.427800,  0.000000
 2.0,  0.0, -2.0, -1.0 =>  1.581139,  0.000000, -0.632456, -0.316228
 1.0,  1.0,  1.0,  1.0 =>  1.224745,  0.408248,  0.408248,  0.408248
 0.1,  0.2,  0.3,  0.4 =>  0.569088,  0.175720,  0.263580,  0.351439
99.0,  0.0,  0.0,  0.1 =>  9.949876,  0.000000,  0.000000,  0.005025

Generato usando questo script Python . È stata specificata solo una delle due risposte corrette per ciascun caso di test; l'altro è tutti e quattro i valori negati.

Punteggio e criterio di vincita

Si applicano le regole standard del . Vince il programma o la funzione più breve in byte in ogni lingua.


Possiamo prendere il quaternione come a, (b, c, d)?
nwellnhof,

@nwellnhof Certo. Anche qualcosa del genere a,[b,[c,[d]]]va bene, se riesci in qualche modo a salvare byte con esso :)
Bubbler

Risposte:


29

APL (NARS) , 2 byte

NARS ha il supporto integrato per i quaternioni. ¯ \ _ (⍨) _ / ¯


4
Non posso farci niente: dovresti includere "¯ _ (ツ) _ / ¯" nella tua risposta
Barranka,

7
Hai lasciato cadere questo \
Andrew il

@Barranka Fatto.
Adám,

@Andrew biasimalo sull'app per Android ... Grazie per averlo raccolto :)
Barranka

2
Sarebbe meglio se fosse¯\_(⍨)√¯
Zacharý

8

Python 2 , 72 byte

def f(a,b,c,d):s=((a+(a*a+b*b+c*c+d*d)**.5)*2)**.5;print s/2,b/s,c/s,d/s

Provalo online!

Più o meno una formula grezza. Pensavo di poter usare la comprensione dell'elenco per fare un giro b,c,d, ma questo sembra essere più lungo. Python è davvero ferito qui dalla mancanza di operazioni vettoriali, in particolare il ridimensionamento e la norma.

Python 3 , 77 byte

def f(a,*l):r=a+sum(x*x for x in[a,*l])**.5;return[x/(r*2)**.5for x in[r,*l]]

Provalo online!

Anche la risoluzione diretta del quadratico è stata più breve rispetto all'utilizzo della radice quadrata a numero complesso di Python per risolverlo come nell'affermazione del problema.


"L'input è un quaternione non reale. Puoi prenderlo come quattro numeri reali (in virgola mobile), in qualsiasi ordine e struttura di tua scelta." Quindi puoi considerarlo una serie di panda o una matrice numpy. Le serie hanno il ridimensionamento con una semplice moltiplicazione e ci sono vari modi per ottenere la norma, come ad esempio (s*s).sum()**.5.
Accumulo

6

Wolfram Language (Mathematica) , 19 byte

Sqrt
<<Quaternions`

Provalo online!

Mathematica ha anche Quaternion integrato, ma è più dettagliato.


Sebbene i built-in abbiano un aspetto accattivante, fai soluzioni di voto che non usano anche i built-in! Non voglio che i voti su domande che arrivano a HNQ siano distorti.


4

JavaScript (ES7), 55 53 byte

Basato sulla formula diretta utilizzata da xnor .

Accetta input come un array.

q=>q.map(v=>1/q?v/2/q:q=((v+Math.hypot(...q))/2)**.5)

Provalo online!

Come?

q=[a,b,c,d]

x=a+a2+b2+c2+d22

E ritorna:

[x,b2x,c2x,d2x]

q =>                            // q[] = input array
  q.map(v =>                    // for each value v in q[]:
    1 / q ?                     //   if q is numeric (2nd to 4th iteration):
      v / 2 / q                 //     yield v / 2q
    :                           //   else (1st iteration, with v = a):
      q = (                     //     compute x (as defined above) and store it in q
        (v + Math.hypot(...q))  //     we use Math.hypot(...q) to compute:
        / 2                     //       (q[0]**2 + q[1]**2 + q[2]**2 + q[3]**2) ** 0.5
      ) ** .5                   //     yield x
  )                             // end of map()

3

Haskell , 51 byte

f(a:l)|r<-a+sqrt(sum$(^2)<$>a:l)=(/sqrt(r*2))<$>r:l

Provalo online!

Una formula diretta Il trucco principale per esprimere la parte reale dell'output è quello r/sqrt(r*2)di parallelizzare l'espressione della parte immaginaria, che consente di risparmiare qualche byte su:

54 byte

f(a:l)|s<-sqrt$2*(a+sqrt(sum$(^2)<$>a:l))=s/2:map(/s)l

Provalo online!


3

Carbone , 32 byte

≔X⊗⁺§θ⁰XΣEθ×ιι·⁵¦·⁵η≧∕ηθ§≔θ⁰⊘ηIθ

Provalo online! Il collegamento è alla versione dettagliata del codice. Port of @ xnor's Python answer. Spiegazione:

≔X⊗⁺§θ⁰XΣEθ×ιι·⁵¦·⁵η

|x+yu|=x2+y2=(a2b2)2+(2ab)2=a2+b2x2a22a

≧∕ηθ

y=2abb2a

§≔θ⁰⊘η

2a

Iθ

Trasmetti i valori in stringa e stampa implicitamente.


3

Java 8, 84 byte

(a,b,c,d)->(a=Math.sqrt(2*(a+Math.sqrt(a*a+b*b+c*c+d*d))))/2+" "+b/a+" "+c/a+" "+d/a

Porta della risposta Python 2 di @xnor .

Provalo online.

Spiegazione:

(a,b,c,d)->           // Method with four double parameters and String return-type
  (a=                 //  Change `a` to:
     Math.sqrt(       //   The square root of:
       2*             //    Two times:
         (a+          //     `a` plus,
          Math.sqrt(  //     the square-root of:
            a*a       //      `a`  squared,
            +b*b      //      `b` squared,
            +c*c      //      `c` squared,
            +d*d))))  //      And `d` squared summed together
  /2                  //  Then return this modified `a` divided by 2
  +" "+b/a            //  `b` divided by the modified `a`
  +" "+c/a            //  `c` divided by the modified `a`
  +" "+d/a            //  And `d` divided by the modified `a`, with space delimiters

2

05AB1E , 14 byte

nOtsн+·t©/¦®;š

Porta della risposta Python 2 di @xnor .

Provalo online o verifica tutti i casi di test .

Spiegazione:

n                 # Square each number in the (implicit) input-list
 O                # Sum them
  t               # Take the square-root of that
   sн+            # Add the first item of the input-list
      ·           # Double it
       t          # Take the square-root of it
        ©         # Store it in the register (without popping)
         /        # Divide each value in the (implicit) input with it
          ¦       # Remove the first item
           ®;     # Push the value from the register again, and halve it
             š    # Prepend it to the list (and output implicitly)


2

C #. NET, 88 byte

(a,b,c,d)=>((a=System.Math.Sqrt(2*(a+System.Math.Sqrt(a*a+b*b+c*c+d*d))))/2,b/a,c/a,d/a)

Porta della mia risposta Java 8 , ma restituisce una Tupla invece di una Stringa. Ho pensato che sarebbe stato più breve, ma sfortunatamente è Math.Sqrtnecessario un System-import in C # .NET, che finisce con 4 byte in più invece di 10 byte in meno ..>.>

La dichiarazione lambda sembra piuttosto divertente, però:

System.Func<double, double, double, double, (double, double, double, double)> f =

Provalo online.


1

Perl 6 , 49 byte

{;(*+@^b>>².sum**.5*i).sqrt.&{.re,(@b X/2*.re)}}

Provalo online!

Funzione Curry prendendo input come f(b,c,d)(a). Restituisce quaternione come a,(b,c,d).

Spiegazione

{;                                             }  # Block returning WhateverCode
     @^b>>².sum**.5     # Compute B of quaternion written as q = a + B*u
                        # (length of vector (b,c,d))
  (*+              *i)  # Complex number a + B*i
                      .sqrt  # Square root of complex number
                           .&{                }  # Return
                              .re,  # Real part of square root
                                  (@b X/2*.re)  # b,c,d divided by 2* real part
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.