Search code examples
perlcomplex-numberspdl

Transpose in Perl's PDL::Complex


I am considering the complex extension of the Perl Data Language (PDL 2.19.0) for complex matrix operations, but operations as easy as transpose do not work as I would expect.

use strict;
use warnings;

use PDL;
use PDL::Complex;

my $m = cplx pdl [i, 1], [-1, -i];

printf "m=%s\n", $m; 
my $mt = $m->transpose;
printf "m=%s\n", $m; 
printf "mt=%s\n", $mt;
my $mx = $m->xchg(1,2);
printf "m=%s\n", $m; 
printf "mx=%s\n", $mx;

To me it seems that $m->transpose equals $m. Another supposedly easy operation which bugs me:

printf "m[0,0]=%s\n", $m->at(0,0);

does not work, only

printf "m[0,0,0]=%s\n", $m->at(0,0,0);

does. Am I using the API in a wrong way?


Solution

  • The basic piddle operations don't behave as you expect because it looks like complex piddles are implemented using the 0th dimension to store the real and imaginary pair. You can see this if you check dims or real:

    pdl> $m = cplx pdl [i, 1], [-1, -i];
    
    pdl> p $m->dims
    2 2 2
    pdl> p $m->real
    
    [
     [
      [0 1]
      [1 0]
     ]
     [
      [-1  0]
      [ 0 -1]
     ]
    ]
    

    Thus, you can use xchg instead of transpose to transpose the correct dimensions of the "two-dimensional" complex piddle:

    pdl> p $m
    
    [
     [ 0 +1i   1 +0i]
     [-1 +0i   0 -1i]
    ]
    
    pdl> p $m->xchg(1, 2)
    
    [
     [ 0 +1i  -1 +0i]
     [ 1 +0i   0 -1i]
    ]
    
    

    For at, you can get the real/imaginary parts separately and combine them:

    pdl> p cplx pdl $m->at(0,0,0), $m->at(1,0,0)
    0 +1i
    

    Or slice the pair:

    pdl> p $m->slice('', '(0)', '(0)')
    0 +1i