3

The C++ language provides a general template-based implementation of complex numbers. Normally, these are using to manipulate numbers of the form $a + b i$, where $a, b$ are chosen as either 32 or 64 bit floating point numbers. These are respectively denoted by std::complex<float> and std::complex<double>. The language implements the standard multiplication, division, addition etc. operators on complex numbers.

Because the code provided to manipulate complex numbers is general, we can embed complex numbers within complex numbers, e.g. using std::complex<std::complex<double>>, nesting arbitrarily deeply. The doubly nested data type is uniquely defined by four floating point numbers. It is thus representing numbers in a form $(a + b i) + (c + d i) j$, where $i^2 = -1$, $j^2 = -1$, and $a, b, c, d \in \mathbb{R}$.

I initially thought these would be related to quaternions, but the structure encountered here is not anti-commutative in the $i, j$ basis units which is apparently a property of quaternions. On top of that, these seem to not be equivalent to bicomplex numbers, because there is no third analog of the imaginary unit present, named $k$ in this article. I get the suspicion that std::complex<std::complex<double>> is isomorphic to the complex numbers after reading the Frobenius theorem about real division algebras.

Is this the correct conclusion? If so, why? If not, what algebraic structure is std::complex<std::complex<double>> isomorphic to?

Bill Dubuque
  • 272,048
  • 4
    By CRT $,\Bbb C[j]/(j^2+1) \cong C[j]/(j-i) \times \Bbb C[j]/(j+i)\cong \Bbb C^2\ \ $ – Bill Dubuque Feb 10 '23 at 18:15
  • Pardon my lack of algebra knowledge, but what is $\mathbb{C}[j]/(j^2+1)$ ? You're saying this is isomorphic to $\mathbb{C}^2$? – Gavin Ridley Feb 10 '23 at 18:36
  • (1) According to https://en.cppreference.com/w/cpp/numeric/complex , "we can embed complex numbers within complex numbers" is NOT true [ template Parameter must be float, double, or long double ] (2) In Case your Implementation supports arbitrary template Parameter , Eg std::complex<std::complex> , you might want to check abs , norm , arg , polar to see what that Structure is Isomorphic to. [[CONTINUED]] – Prem Feb 10 '23 at 18:49
  • 3
    It's the quotient of the polynomial ring $\Bbb C[j]$ by its ideal $(j^2+1),,$ i.e. said polynomials mod $,j^2\equiv -1,,$ just like Hamiltons pair construction $\Bbb C \cong \Bbb R[i]/(i^2+1),$ (or, w/o notation abuse, $\Bbb C\cong \Bbb R[x]/(x^2+1),,$ where $,i = \bar x := x+(x^2+1),$ denotes the image of $,x,$ in the quotient ring); i.e. we iterate the same construction that we used to create $\Bbb C$ from $\Bbb R,,$ just as you do in C++. Please give more context, e.g. do you know any ring theory? – Bill Dubuque Feb 10 '23 at 18:50
  • [[CONTINUED]] (3) In Case , this is not C++ Question , you might want to remove all that & highlight the Part "The doubly nested data type is uniquely defined by four floating point numbers." (4) You might then include what operations you want , to see what that Structure is Isomorphic to. (5) Otherwise , we are Discussing non-Existent Structure which is not well Defined. – Prem Feb 10 '23 at 18:53
  • 1
    @Prem, the operations I had in mind are defined by introducing the $i$ and $j$ I identified in the post, and I've verified that my compiler indeed produces operations in line with this definition. Besides, the template parameter can be any numeric type, it's just that behavior is undefined and left to be explored by the user in the event it's not float, double, or long double. I'm not planning to write production code employing this behavior, but rather sought only to explore the behavior exhibited by std::complex<std::complex<double>>. – Gavin Ridley Feb 10 '23 at 19:00
  • Thank you @BillDubuque, this has provided me with enough keywords to learn further on my own. – Gavin Ridley Feb 10 '23 at 19:02
  • Your Compiler is supporting that , hence you should check the outputs of "abs , norm , arg , polar" to get the "Isomorphism". Either you Define the operations or let your Compiler Define the operations , not both , unless the Definitions are "Equivalent". – Prem Feb 10 '23 at 19:13
  • @Prem This is not the correct place to discuss C++ specifics. The question concerns the mathematics, not limitations of the C++ implementation (which is off topic here), – Bill Dubuque Feb 10 '23 at 19:20
  • The product demomposition in my first comment happens generally when we adjoin to a field a third root of a quadratic that already has two distinct roots in the field, e.g. see here on adjoining a "sign" $,s = \pm1,,$ where we get a product ring representing a pair of two possible universes (rings), one world where $s = -1$ and a second world where $s = 1,,$ and operations are done in parallel (componentwise) in both worlds. These are prototypical examples of CRT ring factorizations (see the link in my first comment). – Bill Dubuque Feb 10 '23 at 19:25
  • That is my Exact Point , @BillDubuque , where my Earlier Comments were trying to ask OP to remove such Content & focus on the Part "The doubly nested data type is uniquely defined by four floating point numbers" + "include what operations you want , to see what that Structure is Isomorphic to" : the C++ template in the Question Post is entirely unrelated to the Query at hand. – Prem Feb 10 '23 at 19:45
  • 1
    @Gavin The answer you accepted uses concepts unlikley to be familiar at the level of your question (e.g. tensor products). If you are interested in simpler / better explanations then you should unaccept it (many readers don't browse questions with accepted answers). Generally it's a good idea to wait at least a few days before accepting an answer. – Bill Dubuque Feb 10 '23 at 20:05
  • OK, thank you for the recommendation. I've done that, and will pick the best after a few days without an answer. I do understand tensor products, but just have never taken an abstract algebra class. – Gavin Ridley Feb 10 '23 at 21:01
  • Heh, I've taken two undergraduate abstract algebra classes, and algebraic topology, and still am not sure I understand tensor products. – JonathanZ Feb 10 '23 at 21:41

2 Answers2

2

This structure cannot possibly be isomorphic to complex numbers; as you say yourself, it is four-dimensional over $\mathbb R$ while the complex numbers are two dimensional.

What you're missing is that the bicomplex $j, k$ from the article you linked have $j^2 = 1$ and $k^2 = -1$, but your $j$ has $j^2 = -1$. So take your $i,j$ and define $$ i' = i,\quad j' = ij,\quad k' = j. $$ You will find using the basis $1,i',j',k'$ that your algebra is the bicomplex numbers exactly as described in the article.

1

In the structure $\Bbb C\otimes_{\Bbb R}\Bbb C$ you get $i^2+1=j^2+1=0$ and thus also $i^2-j^2=0$, identifying $i\otimes 1$ with $i$ and $1\otimes j$ with $j$. This means that $$(i+j)(i-j)=0,$$ so you get zero-divisors. In a further step, as also $(ij)^2=1$, $$P_\pm=\frac12(1\pm ij)$$ are projectors on sub-spaces of $\Bbb C\otimes_{\Bbb R}\Bbb C$ where $i$ acts like $\pm j$, so the space decomposes into the vector-space sum of two "cross-diagonal" copies of $\Bbb C$.

Lutz Lehmann
  • 126,666
  • The weird thing is is that I'm pretty sure that the complex<> template provides a division binary operation. All us math people are automatically thinking "Well, it's not going to be a field", but I'm left wondering what's going to happen when you invoke operator/. – JonathanZ Feb 10 '23 at 19:15
  • 1
    You get division by zero if the divisor is a multiple of a zero-divisor. For almost all random elements this is not the case. – Lutz Lehmann Feb 10 '23 at 19:22
  • 1
    Ah, the modulus operator, which I'd guess is used to find inverses and do division, is $|z_1+z_2j|^2=z_1^2+z_2^2$, not $|z_1|^2+|z_2|^2$. – JonathanZ Feb 10 '23 at 19:30
  • Per my comment on the question: as a ring it is $\cong \Bbb C^2,,$ which has many zero divisors $(c,0)$ and $(0,c)$, so it's not at all clear what your remark about "almost all random elements" is intended to mean. – Bill Dubuque Feb 10 '23 at 19:53
  • 1
    @Bill : That is correct. The zero divisors live in the union of two real-two-dimensional subspaces. In the surrounding real-4-dimensional space this is a very thin set. – Lutz Lehmann Feb 10 '23 at 20:03
  • What precisely do you mean by "thin". By what definition are the axes "thin" in $\Bbb Z^2$ or $,\Bbb Z_p^2$? $\ \ $ – Bill Dubuque Feb 10 '23 at 20:15
  • 1
    @Bill : Considering the spaces as real vector spaces, any set $X$ of dimension 2 in a vector space $M$ of dimension 4 has measure zero. Almost every point of $M$ does not belong to $X$. – Lutz Lehmann Feb 10 '23 at 20:17
  • But that doesn't generalize to product rings, e.g. the simple examples I gave above. It's best to avoid imprecise random remarks like that since they can easily mislead beginners. – Bill Dubuque Feb 10 '23 at 20:25
  • @BillDubuque - See, I think there is something going on here. I checked the (GNU) implementation, and I'm pretty sure $1/(c,0)$ (if you'll forgive that notation) is just going to return $(1/c,0)$, as it just blindly does a "conjugate and divide by modulus squared". – JonathanZ Feb 10 '23 at 20:30
  • @Readers For a commutative ring $R$ with zero divisors $R_z,$ it is easy to show that if $R$ is infinite then $|R_z| = |R|,,$ and if $R$ is finite then $,|R_z| \ge \sqrt{|R|},,$ e.g. see Gilmer's Monthly paper Zero Divisors in Commutative Rings for these and more precise results. So there are many more ways for division-by-zero(-divisor) errors to arise in general commutative rings (vs. only $1$ way in a field or domain). – Bill Dubuque Feb 10 '23 at 22:45