16
$\begingroup$

Consider a multi-value function $f(z)=\sqrt{(z-a)(z+\bar a)}, \Im{a}>0,\Re{a}>0$. To make the function be single-valued, one needs to make a cut. Suppose $a=e^{i\theta}$, my choice of the branch cut is $e^{it},t\in (\theta,\pi-\theta)$. This uniquely defines my function $f(z)$, now I want to study the level curves of $f$, and how to visualize it on Mathematica?

Note: How to Choose a branch so that the cut is part of the level curve (say $\Im f=0$).

Update: In fact, since we know the effect of passing the cut is changing sign. We thus can define the radical by the following Riemann-Hilbert Problem: $$R_+=-R_-(z),\quad z\in \Gamma,$$ where $\Gamma$ is any branch cuts you want. Then up to some proper normalization, the solution is $$\exp\{h(z)+C_\Gamma(\log(-1))(z)\},$$ where $C_\Gamma$ is the Cauchy transform. If the branch cut is properly parametrized, the integral can be computed in Mathematica using NIntegrate.

$\endgroup$
2
  • 1
    $\begingroup$ Please provide references, preferably books. $\endgroup$
    – cvgmt
    Aug 17, 2022 at 23:48
  • 1
    $\begingroup$ @cvgmt there’s no specific reference. Any complex analysis book will mention this topic. More advanced one can check books about Riemann surfaces (Alfhors, Springer, and so on) $\endgroup$
    – DuFong
    Aug 18, 2022 at 0:51

3 Answers 3

8
$\begingroup$

Update

Here's a simplified numerical way, by integrating an ODE without branch points from the origin to $z$, determining the sign by whether the path crosses the branch cut (update 2: originally, I used WhenEvent to keep track of the sign, and it might be needed when the branch cut is more complicated but still described by an equation; in this case I realized that the example branch cut is particularly simple to deal with; see edit history for the WhenEvent approach).

With[{w = Exp[I Pi/3]},
 ndSqrt[z0_?NumericQ] := Block[{z, t, u, sign},
   NDSolveValue[
    {D[u[t]^2 == (z - w) (z + Conjugate[w]) /. z -> t*z0, t],
     u[0] == Sqrt[(0 - w) (0 + Conjugate[w])]},
    If[Pi/3 < Arg[z0] < 2 Pi/3 && Abs@z0 > 1, -1, 1] u[1],
    {t, 0, 1}]]
 ]

You can just plot Re@ndSqrt[z] and Im@ndSqrt[z], since the argument to the square root is built into the ODE.


Original answer

This is my interpretation of what is wanted, at least as far as drawing a picture goes. A PIA to construct the branch cut, since the default branch cut of Sqrt[(z - w) (z + Conjugate[w])] is the imaginary axis plus the line segment joining the branch points, perhaps its construction can be improved.

Block[{w = Exp[I Pi/3](*,z=x+I y*)},
 branchcut =
  Piecewise[{{1, -1/2 < x < 0 && -1/2 < y < 1/2 && 
        First@GroebnerBasis[(z - w) (z + Conjugate[w]) /. 
                 z -> Exp[I t] // ReIm // # == {x, y} & // 
              ComplexExpand //
             # /. {Cos[t] -> a, Sin[t] -> b} & // {#, 
              a^2 + b^2 == 1} &, {x, y}, {a, b}
           ] > 0}},
     -1] /. {x -> Re[z], y -> Im[z]} // FullSimplify
 ]

Block[{w = Exp[I Pi/3](*,z=x+I y*)},
 mySqrt[z_] = -Sqrt[z] (2 UnitStep@Im[z] - 1) branchcut
 ]

Block[{w = Exp[I Pi/3], z = x + I y},
 GraphicsRow[{
   Plot3D[
    Im[mySqrt[(z - w) (z + Conjugate[w])] Piecewise[{{-1, 
         Im[z] > Im[w] || Im[z] <= Im[w] && Abs[z - 2 Im[w] I] < 1}}, 
       1]],
    {x, -3/2, 3/2}, {y, -1/2, 3/2},
    AxesLabel -> {HoldForm@Re[z], HoldForm@Im[z]}, 
    Exclusions -> {{x^2 + y^2 == 1, -1/2 < x < 1/2 && y > 0}},
    ViewPoint -> {1.3, 2.4, 2.}, 
    AxesEdge -> {{1, -1}, {-1, 1}, {-1, 1}},
    MeshFunctions -> {#3 &}, 
    MeshShading -> ColorData["SolarColors"] /@ Subdivide[0., 1., 15]
    ],
   Plot3D[
    Re[mySqrt[(z - w) (z + Conjugate[w])] Piecewise[{{-1, 
         Im[z] > Im[w] || Im[z] <= Im[w] && Abs[z - 2 Im[w] I] < 1}}, 
       1]],
    {x, -3/2, 3/2}, {y, -1/2, 3/2},
    AxesLabel -> {HoldForm@Re[z], HoldForm@Im[z]}, 
    Exclusions -> {{x^2 + y^2 == 1, -1/2 < x < 1/2 && y > 0}},
    ViewPoint -> {1.3, 2.4, 2.}, 
    AxesEdge -> {{1, -1}, {-1, 1}, {-1, 1}},
    MeshFunctions -> {#3 &}, 
    MeshShading -> ColorData["SolarColors"] /@ Subdivide[0., 1., 15]
    ]
   }]
 ]

enter image description here

With ContourPlot:

enter image description here

$\endgroup$
1
  • 2
    $\begingroup$ Nicely and elegantly done. Always a pleasure! $\endgroup$
    – josh
    Aug 17, 2022 at 17:48
13
$\begingroup$

Edit3: Added a ComplexContourPlot of level curves over radial branch region. See below

With these problems I find it helpful to draw the function in its entirety then decide how to cut out an analytically-continuous single-valued section of it. Unfortunately in this case it's a little difficult to do this with the built-in functions as they rely on default branch-cuts which cause imperfections of the plots when done so globally but we can plot around the cut to remedy this. First identify the default branch-cut of the function. I'll use $\theta=\pi/4$:

f[z_, a_] := Sqrt[(z - a) (z + Conjugate[a])]
theta = Pi/4;
Reduce[Arg[(z - Exp[I theta]) (z + Exp[-I theta])] == Pi, z]

(* (-(1/Sqrt[2]) < Re[z] < 0 && Im[z] == 1/Sqrt[2]) || 
 Re[z] == 0 || (0 < Re[z] < 1/Sqrt[2] && Im[z] == 1/Sqrt[2]) *)

That's basically a line in the z-plane from the point $(-1/\sqrt{2},1/\sqrt{2})$ to $(1/\sqrt{2},1/\sqrt{2})$. Now we can use Plot3D to plot around this line and thereby never incurring the default branch-cut (little messy but if you take your time and study the plots you'll understand it). Below I plot 16 color-coded sections of the function Im[f] to make it easier to see the surfaces.

 sa = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 1/Sqrt[2], 2}, {y, 
    1/Sqrt[2], 2}, PlotStyle -> Darker@Yellow];
sb = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 0, 1/Sqrt[2]}, {y, 
    1/Sqrt[2], 2}, PlotStyle -> Orange];
sc = Plot3D[-Im@f[z, Exp[I theta]] /. z -> x + I y, {x, -1/Sqrt[2], 
    0}, {y, 1/Sqrt[2], 2}, PlotStyle -> Red];
sd = Plot3D[-Im@f[z, Exp[I theta]] /. 
    z -> x + I y, {x, -2, -1/Sqrt[2]}, {y, 1/Sqrt[2], 2}, 
   PlotStyle -> Green];
se = Plot3D[-Im@f[z, Exp[I theta]] /. 
    z -> x + I y, {x, -2, -1/Sqrt[2]}, {y, -2, 1/Sqrt[2]}, 
   PlotStyle -> Yellow];
sf = Plot3D[-Im@f[z, Exp[I theta]] /. z -> x + I y, {x, -1/Sqrt[2], 
    0}, {y, -2, 1/Sqrt[2]}, PlotStyle -> Purple];
sg = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 0, 1/Sqrt[2]}, {y, -2, 
    1/Sqrt[2]}, PlotStyle -> Magenta];
sh = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 1/Sqrt[2], 2}, {y, -2, 
    1/Sqrt[2]}, PlotStyle -> Brown];

sa2 = Plot3D[-Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 1/Sqrt[2], 
    2}, {y, 1/Sqrt[2], 2}, PlotStyle -> Darker@Yellow];
sb2 = Plot3D[-Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 0, 
    1/Sqrt[2]}, {y, 1/Sqrt[2], 2}, PlotStyle -> Orange];
sc2 = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, -1/Sqrt[2], 0}, {y, 
    1/Sqrt[2], 2}, PlotStyle -> Red];
sd2 = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, -2, -1/Sqrt[2]}, {y, 
    1/Sqrt[2], 2}, PlotStyle -> Green];
se2 = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, -2, -1/Sqrt[2]}, {y, -2,
     1/Sqrt[2]}, PlotStyle -> Yellow];
sf2 = Plot3D[
   Im@f[z, Exp[I theta]] /. z -> x + I y, {x, -1/Sqrt[2], 0}, {y, -2, 
    1/Sqrt[2]}, PlotStyle -> Purple];
sg2 = Plot3D[-Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 0, 
    1/Sqrt[2]}, {y, -2, 1/Sqrt[2]}, PlotStyle -> Magenta];
sh2 = Plot3D[-Im@f[z, Exp[I theta]] /. z -> x + I y, {x, 1/Sqrt[2], 
    2}, {y, -2, 1/Sqrt[2]}, PlotStyle -> Brown];
multiBranchPlot=Show[{sa, sb, sc, sd, se, sf, sg, sh, sa2, sb2, sc2, sd2, se2, sf2, 
  sg2, sh2}, PlotRange -> 2, BoxRatios -> {1, 1, 1}, 
 PlotLabel -> Style["Im(f)", 16, Bold, Black]]

enter image description here

Now it's easy to plot a single-valued section of the function with branch-cut for example $(-1/\sqrt{2},1/\sqrt{2})$:

enter image description here

Or a single-valued section with branch cuts $(-\infty,-1/\sqrt{2})\bigcup (1/\sqrt{2},\infty)$: enter image description here

And here is one of two (analytically-continuous, single-valued) branches described by OP in the region $(\pi-\theta,\theta)$:

theColor = Darker@Blue;
pp1 = ParametricPlot3D[{Re@z, Im@z, Im@f[z, Exp[I theta]]} /. 
    z -> r Exp[I t], {r, 0, 2}, {t, theta, Pi/2}, 
   RegionFunction -> Function[{x, y, z}, y > 1/Sqrt[2] + 0.005], 
   PlotPoints -> 100, PlotStyle -> theColor];
pp2 = ParametricPlot3D[{Re@z, Im@z, -Im@f[z, Exp[I theta]]} /. 
    z -> r Exp[I t], {r, 0, 2}, {t, theta, Pi/2}, 
   RegionFunction -> Function[{x, y, z}, y < 1/Sqrt[2] - 0.005], 
   PlotPoints -> 100, PlotStyle -> theColor];
pp3 = ParametricPlot3D[{Re@z, Im@z, -Im@f[z, Exp[I theta]]} /. 
    z -> r Exp[I t], {r, 0, 2}, {t, Pi/2, Pi - theta}, 
   RegionFunction -> Function[{x, y, z}, y > 1/Sqrt[2] + 0.005], 
   PlotPoints -> 100, PlotStyle -> theColor];
pp4 = ParametricPlot3D[{Re@z, Im@z, Im@f[z, Exp[I theta]]} /. 
    z -> r Exp[I t], {r, 0, 2}, {t, Pi/2, Pi - theta}, 
   RegionFunction -> Function[{x, y, z}, y < 1/Sqrt[2] - 0.005], 
   PlotPoints -> 100, PlotStyle -> theColor];

radialBranch = 
 Show[{pp1, pp2, pp3, pp4}, PlotRange -> 2, BoxRatios -> {1, 1, 1}]

comboPlot = 
 Show[{radialBranch, multiBranchPlot, radialPlot}, 
  PlotLabel -> Style["Im(f) with radial branch", 16, Black, Bold]]

enter image description here

Edit 3: Level curve plot over radial branch defined by sector $e^{it}, \theta<t<\pi-\theta$:

This is the code to generate level-curves over the sector branch I described below. Have to use `ComplexContourPlot over the appropriate regions to assure continuity of the level curves. The two black diagonal lines are the branch cuts of the indicated branch, red points are the singular points. Note the branch cuts do not make contact with singular points but only appear so in the plot.

line1G = Graphics@Line[{{0, 0}, ReIm@(-2 + 2 I)}];
line2G = Graphics@Line[{{0, 0}, ReIm@(2 + 2 I)}];
s1G = Graphics@{PointSize[0.025], Red, Point@{-1/Sqrt[2], 1/Sqrt[2]}};
s2G = Graphics@{PointSize[0.025], Red, Point@{1/Sqrt[2], 1/Sqrt[2]}};
ccpTable = Table[
   ccp1 = 
    ComplexContourPlot[
     Im@f[z, Exp[I theta]] == levelVal, {z, 0, 2 + 2 I}];
   ccp2 = 
    ComplexContourPlot[-Im@f[z, Exp[I theta]] == levelVal, {z, -2, 
      2 I}];
   {ccp1, ccp2},
   {levelVal, 1/10, 15/10, 1/10}
   ];
ccpTable2 = Table[
   ccp1 = 
    ComplexContourPlot[
     Im@f[z, Exp[I theta]] == levelVal, {z, 0, 2 + 2 I}];
   ccp2 = 
    ComplexContourPlot[-Im@f[z, Exp[I theta]] == levelVal, {z, -2, 
      2 I}];
   {ccp1, ccp2},
   {levelVal, -15/10, -1/10, 1/10}
   ];

Show[{ccpTable, line1G, line2G, s1G, s2G, ccpTable2}, PlotRange -> 2, 
 PlotLabel -> Style["Level curves on Im(f)", 16, Bold, Black]]

enter image description here

$\endgroup$
10
  • $\begingroup$ is it possible to project to the complex plane (say, replace Plot3D by ContourPlot?) $\endgroup$
    – DuFong
    Aug 16, 2022 at 20:57
  • $\begingroup$ @DuFong: Sorry, I don't understand your question. Maybe you can explain further. Also there is likely an analytic method of directly representing a desired branch by an analytic expression using perhaps $z_1=r_1e^{i t_1}$ and $z_2=r_2 e^{i t_2}$ in the expression for $f$. $\endgroup$
    – josh
    Aug 17, 2022 at 10:56
  • $\begingroup$ @DuFong, josh: I'd expect to see each plot of the real and imaginary parts to be a surface over the complex plane with a discontinuity only along the arc of the unit circle parametrized by $z=e^{it}$, $\theta \le t \le \pi-\theta$, according how I've understood the question. But I haven't yet thought of an approach that is simple enough I want to try it. — Is that the right idea, though? $\endgroup$
    – Michael E2
    Aug 17, 2022 at 14:09
  • $\begingroup$ @Michael E2: There is no discontinuity between the radial branch $\theta<t<\pi-\theta$ as I've drawn it above and the remainder of the multivalued sheets. That radial section is simply an analytic domain of the function which does not involve any of its singular points which is equivalent to taking the disc $1+1/2 e^{it}$ out of $\sqrt{z}$ . $\endgroup$
    – josh
    Aug 17, 2022 at 14:21
  • $\begingroup$ And so what you drew is incorrect? Or rather, not in agreement with my understanding of the question? — I was thinking that @DuFong would clarify. I'm just surprised that there is no discontinuity along the proposed branch cut. $\endgroup$
    – Michael E2
    Aug 17, 2022 at 14:40
9
$\begingroup$

Perhaps you can use ComplexPlot (since v12)

ClearAll[f] ;
f[w_][z_] := Sqrt[(z - w)(z + Conjugate[w])] ;

Manipulate[
    ComplexPlot[
        f[Exp[I*theta]][z], 
        {z,-5 - 5I, 5 + 5I}, 
        PlotPoints -> 100,
        MaxRecursion -> 2,
        ColorFunction -> "CyclicLogAbsArg",
        PlotLegends -> Automatic
    ],
    {theta, 0, 2*Pi, 0.1*Pi},
    ContinuousAction -> False
]

enter image description here

$\endgroup$
3
  • 2
    $\begingroup$ Thanks for your solution. But Mathematica uses its default branch cut, which is the straight line connecting two branch points, unfortunately, it is not my case. $\endgroup$
    – DuFong
    Aug 16, 2022 at 16:12
  • 1
    $\begingroup$ @I.M. can you get rid of the aliasing and make it higher resolution? $\endgroup$
    – M.R.
    Aug 16, 2022 at 19:05
  • 1
    $\begingroup$ See mathematica.stackexchange.com/q/239230/4999 (@M.R.) $\endgroup$
    – Michael E2
    Aug 16, 2022 at 23:43

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.