Published
Edited
Mar 15, 2020
11 stars
Insert cell
Insert cell
class Complex16 extends Float64Array {
constructor(...args) {
super(...args);
if (this.length !== 2) {
throw new Error('invalid complex number');
}
}
// setters
set re(value) { this[0] = value; }
set im(value) { this[1] = value; }
// getters
get re() { return this[0]; }
get im() { return this[1]; }
// for visualization purposes only
toString() {
const { im, re } = this;

let real = '';
if (re !== 0 || im === 0) {
real = re;
}
let op = '';
if (re !== 0 && im > 0) {
op = '+';
}
let imaginary = '';
if (im !== 0) {
if (im === 1) {
imaginary = `i`;
} else if (im === -1) {
imaginary = `-i`
} else {
imaginary = `${im}i`;
}
}

return `${real}${op}${imaginary}`;
}
}
Insert cell
Insert cell
{
const z = new Complex16(2);
z.re = 4;
z.im = 3;

return tex.block`
\begin{aligned}
z &= ${z} \\
\operatorname{Re}(z) &= ${z.re} \\
\operatorname{Im}(z) &= ${z.im} \\
\end{aligned}
`;
}
Insert cell
Insert cell
Insert cell
function add(z1, z2) {
return new Complex16([
z1.re + z2.re,
z1.im + z2.im
]);
}
Insert cell
{
const z1 = new Complex16([2, 1]);
const z2 = new Complex16([3, 1]);

return tex.block`
\begin{aligned}
z_1 &= ${z1} \\
z_2 &= ${z2} \\
z_1+z_2 &= ${add(z1, z2)}
\end{aligned}
`;
}
Insert cell
Insert cell
Insert cell
function mul(z1, z2) {
return new Complex16([
z1.re * z2.re - z1.im * z2.im,
z1.re * z2.im + z1.im * z2.re
]);
}
Insert cell
{
const z1 = new Complex16([2, -1]);
const z2 = new Complex16([3, 1]);

return tex.block`
\begin{aligned}
z_1 &= ${z1} \\
z_2 &= ${z2} \\
z_1z_2 &= (${new Complex16([z1.re * z2.re, 0])}) + (${new Complex16([0, z1.re * z2.im])}) + (${new Complex16([0, z1.im * z2.re])}) + (${new Complex16([0, z1.im * z2.im])}^2) \\
&= ${mul(z1, z2)} \\
\end{aligned}
`;
}
Insert cell
Insert cell
Insert cell
function conjg(z) {
return new Complex16([z.re, -z.im]);
}
Insert cell
{
const z = new Complex16([1, 2]);

return tex.block`
\begin{aligned}
z &= ${z} \\
\overline{z} &= ${conjg(z)}
\end{aligned}
`;
}
Insert cell
Insert cell
class Complex16Array extends Float64Array {
constructor(...args) {
super(...args);

if (this.length % 2 !== 0) {
throw new Error('you supplied an uneven amount of elements');
}
}

// get the ith complex number from the vector
get(i) {
const pos = i * 2;
this.checkBounds(pos);
// see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypedArray/subarray
return new Complex16(this.subarray(pos, pos + 2));
}
// set the ith complex number in the vector
set(i, z) {
const pos = i * 2;
this.checkBounds(pos);
this[pos] = z.re;
this[pos + 1] = z.im;
}
// helper to check if accessed index is out of bounds
checkBounds(pos) {
if (pos < 0 || pos > this.length - 2) {
throw new Error('index out of bounds');
}
}
// helper to get count of complex numbers instead of actual length of the array
get size() {
return this.length / 2;
}
// again, just for visualization purposes...
toString() {
const res = [];
for (let i = 0; i < this.size; i++) {
res.push(this.get(i));
}
return `(${res.join(', ')})`;
}
}
Insert cell
Insert cell
{
// allocate new complex vector with 4 memory slots
const u = new Complex16Array(4);
u.set(0, new Complex16([1, 2]));
u.set(1, new Complex16([3, 4]));
const out = [];
for (let i = 0; i < u.size; i++) {
out.push(`u_${i} &= ${u.get(i)} \\\\`);
}
return tex.block`
\begin{aligned}
\vec u &= ${u} \\
${out.join('')}
\end{aligned}
`;
}
Insert cell
Insert cell
Insert cell
function zdotc(n, zx, zy) {
let ztemp = new Complex16([0, 0]);
if (n < 0) {
return ztemp;
}

for (let i = 0; i < n; i++) {
ztemp = add(ztemp, mul(conjg(zx.get(i)), zy.get(i)));
}

return ztemp;
}
Insert cell
{
const n = 3;
const u = new Complex16Array([1, 2, 3, 4, 5, 6]);
const v = new Complex16Array([4, 3, 2, 1, 0, -1]);
return tex.block`
\begin{aligned}
\vec{u} &= ${u} \\
\vec{v} &= ${v} \\
\vec{u}\cdot\vec{v} &= \sum_{i = 0}^n{\overline{u_i} v_i} \\
&= ${zdotc(n, u, v)}
\end{aligned}
`;
}
Insert cell
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more