Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add type hints to Medium class and other improvements and fixes to docs #2554

Merged
merged 3 commits into from
Jun 21, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion doc/docs/Build_From_Source.md
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,7 @@ If you are not the system administrator of your machine, and/or want to install

### Python

If you have Python on your system, then the Meep compilation scripts automatically build and install the `meep` Python module, which works with both the serial and parallel (MPI) versions of Meep. Note: Meep's [visualization module](Python_User_Interface.md#data-visualization) includes animation routines which require [matplotlib](https://matplotlib.org/) version `3.1`+ and the [adjoint solver](Python_Tutorials/Adjoint_Solver.md) requires [autograd](https://github.com/HIPS/autograd).
If you have Python on your system, then the Meep compilation scripts automatically build and install the `meep` Python module, which works with both the serial and parallel (MPI) versions of Meep. Note: Meep's [visualization module](Python_User_Interface.md#data-visualization) includes animation routines which require [matplotlib](https://matplotlib.org/) version `3.1`+ and the [adjoint solver](Python_Tutorials/Adjoint_Solver.md) requires [autograd](https://github.com/HIPS/autograd) version 1.5 or newer.

By default, Meep's Python module is installed for the program `python` on your system. If you want to install using a different Python program, e.g. `python3`, pass `PYTHON=python3` (or similar) to the Meep `configure` script. An Anaconda (`conda`) [package for Meep](Installation.md#conda-packages) is also available on some systems.

Expand Down
4 changes: 2 additions & 2 deletions doc/docs/FAQ.md
Original file line number Diff line number Diff line change
Expand Up @@ -201,9 +201,9 @@ Usage: Fields

### Why are the fields blowing up in my simulation?

Instability in the fields is likely due to one of five causes: (1) [PML](Python_User_Interface.md#pml) overlapping dispersive materials based on a [Drude-Lorentzian susceptibility](Python_User_Interface.md#lorentziansusceptibility) in the presence of [backward-wave modes](https://journals.aps.org/pre/abstract/10.1103/PhysRevE.79.065601) (fix: replace the PML with an [Absorber](Python_User_Interface.md#absorber)), (2) the frequency of a Lorentzian susceptibility term is *too high* relative to the grid discretization (fix: increase the `resolution` and/or reduce the `Courant` factor), (3) a material with a [wavelength-independent negative real permittivity](#why-does-my-simulation-diverge-if-0) (fix: [fit the permittivity to a broadband Drude-Lorentzian susceptibility](#how-do-i-import-n-and-k-values-into-meep)), (4) a grid voxel contains *more than one* dielectric interface (fix: turn off subpixel averaging), or (5) a material with a *wavelength-independent* refractive index between 0 and 1 (fix: reduce the `Courant` factor; alternatively, [fit the permittivity to a broadband Drude-Lorentzian susceptibility](#how-do-i-import-n-and-k-values-into-meep)).
Instability in the fields is likely due to one of five causes: (1) [PML](Python_User_Interface.md#pml) overlapping dispersive materials based on a [Drude-Lorentzian susceptibility](Python_User_Interface.md#lorentziansusceptibility) in the presence of [backward-wave modes](https://journals.aps.org/pre/abstract/10.1103/PhysRevE.79.065601) (fix: replace the PML with an [Absorber](Python_User_Interface.md#absorber)), (2) the frequency of a Lorentzian susceptibility term is *too high* relative to the grid discretization (fix: increase the `resolution` and/or reduce the `Courant` factor), (3) a material with a [wavelength-independent negative real permittivity](#why-does-my-simulation-diverge-if-the-permittivity-is-less-than-0) (fix: [fit the permittivity to a broadband Drude-Lorentzian susceptibility](Materials.md#how-do-i-import-n-and-k-values-into-meep)), (4) a grid voxel contains *more than one* dielectric interface (fix: turn off subpixel averaging), or (5) a material with a *wavelength-independent* refractive index between 0 and 1 (fix: reduce the `Courant` factor; alternatively, [fit the permittivity to a broadband Drude-Lorentzian susceptibility](Materials.md#how-do-i-import-n-and-k-values-into-meep)).

Note: when the fields blow up, the CPU *slows down* due to [floating-point exceptions in IEEE 754](https://en.wikipedia.org/wiki/IEEE_754#Exception_handling). Also, Meep automatically checks the fields at the cell origin after every timestep and [aborts the simulation if the electric energy density has diverged](https://github.com/NanoComp/meep/blob/master/src/step.cpp#L97-L98).
Note: when the fields blow up, the CPU *slows down* due to [floating-point exceptions in IEEE 754](https://en.wikipedia.org/wiki/IEEE_754#Exception_handling). Also, Meep automatically checks the fields at the cell origin after every timestep and aborts the simulation if the electric energy density has diverged.

### How do I compute the steady-state fields?

Expand Down
2 changes: 1 addition & 1 deletion mkdocs.yml
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ markdown_extensions:
- wikilinks
- toc:
title: Table of Contents
permalink: []
permalink: "#"
- attr_list
- fenced_code
- md_in_html
Expand Down
102 changes: 54 additions & 48 deletions python/geom.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,18 @@
from typing import Union, Tuple
"""
A collection of geometry- and material-related objects and helper routines.
"""

from __future__ import annotations

from collections import namedtuple
from copy import deepcopy
import functools
import math
import numbers
from numbers import Number
import operator
from typing import List, NamedTuple, Optional, Type, Tuple, Union
import warnings
from collections import namedtuple
from copy import deepcopy
from numbers import Number

import numpy as np
import meep as mp

Expand Down Expand Up @@ -311,78 +317,78 @@ class Medium:

def __init__(
self,
epsilon_diag=Vector3(1, 1, 1),
epsilon_offdiag=Vector3(),
mu_diag=Vector3(1, 1, 1),
mu_offdiag=Vector3(),
E_susceptibilities=None,
H_susceptibilities=None,
E_chi2_diag=Vector3(),
E_chi3_diag=Vector3(),
H_chi2_diag=Vector3(),
H_chi3_diag=Vector3(),
D_conductivity_diag=Vector3(),
D_conductivity_offdiag=Vector3(),
B_conductivity_diag=Vector3(),
B_conductivity_offdiag=Vector3(),
epsilon=None,
index=None,
mu=None,
chi2=None,
chi3=None,
D_conductivity=None,
B_conductivity=None,
E_chi2=None,
E_chi3=None,
H_chi2=None,
H_chi3=None,
valid_freq_range=FreqRange(min=-mp.inf, max=mp.inf),
epsilon_diag: Vector3 = Vector3(1.0, 1.0, 1.0),
epsilon_offdiag: Vector3 = Vector3(),
mu_diag: Vector3 = Vector3(1.0, 1.0, 1.0),
mu_offdiag: Vector3 = Vector3(),
E_susceptibilities: Optional[List[Type[Susceptibility]]] = None,
H_susceptibilities: Optional[List[Type[Susceptibility]]] = None,
E_chi2_diag: Vector3 = Vector3(),
E_chi3_diag: Vector3 = Vector3(),
H_chi2_diag: Vector3 = Vector3(),
H_chi3_diag: Vector3 = Vector3(),
D_conductivity_diag: Vector3 = Vector3(),
D_conductivity_offdiag: Vector3 = Vector3(),
B_conductivity_diag: Vector3 = Vector3(),
B_conductivity_offdiag: Vector3 = Vector3(),
epsilon: Optional[float] = None,
index: Optional[float] = None,
mu: Optional[float] = None,
chi2: Optional[float] = None,
chi3: Optional[float] = None,
D_conductivity: Optional[float] = None,
B_conductivity: Optional[float] = None,
E_chi2: Optional[float] = None,
E_chi3: Optional[float] = None,
H_chi2: Optional[float] = None,
H_chi3: Optional[float] = None,
valid_freq_range: NamedTuple = FreqRange(min=-mp.inf, max=mp.inf),
):
"""
Creates a `Medium` object.

+ **`epsilon` [`number`]** The frequency-independent isotropic relative
+ **`epsilon` [ `number` ]** The frequency-independent isotropic relative
permittivity or dielectric constant. Default is 1. You can also use `index=n` as
a synonym for `epsilon=n*n`; note that this is not really the refractive index
if you also specify μ, since the true index is $\\sqrt{\\mu\\varepsilon}$. Using
if you also specify $\\mu$, since the true index is $\\sqrt{\\mu\\varepsilon}$. Using
`epsilon=ep` is actually a synonym for `epsilon_diag=mp.Vector3(ep, ep, ep)`.

+ **`epsilon_diag` and `epsilon_offdiag` [`Vector3`]** — These properties allow
+ **`epsilon_diag` and `epsilon_offdiag` [ `Vector3` ]** — These properties allow
you to specify ε as an arbitrary real-symmetric tensor by giving the diagonal
and offdiagonal parts. Specifying `epsilon_diag=Vector3(a, b, c)` and/or
`epsilon_offdiag=Vector3(u, v, w)` corresponds to a relative permittivity ε
`epsilon_offdiag=Vector3(u, v, w)` corresponds to a relative permittivity $\\varepsilon$
tensor \\begin{pmatrix} a & u & v \\\\ u & b & w \\\\ v & w & c \\end{pmatrix}
Default is the identity matrix ($a = b = c = 1$ and $u = v = w = 0$).

+ **`mu` [`number`]** — The frequency-independent isotropic relative permeability
μ. Default is 1. Using `mu=pm` is actually a synonym for `mu_diag=mp.Vector3(pm,
+ **`mu` [ `number` ]** — The frequency-independent isotropic relative permeability
$\\mu$. Default is 1. Using `mu=pm` is actually a synonym for `mu_diag=mp.Vector3(pm,
pm, pm)`.

+ **`mu_diag` and `mu_offdiag` [`Vector3`]** — These properties allow you to
specify μ as an arbitrary real-symmetric tensor by giving the diagonal and
offdiagonal parts exactly as for ε above. Default is the identity matrix.
+ **`mu_diag` and `mu_offdiag` [ `Vector3` ]** — These properties allow you to
specify $\\mu$ as an arbitrary real-symmetric tensor by giving the diagonal and
offdiagonal parts exactly as for $\\varepsilon$ above. Default is the identity matrix.

+ **`D_conductivity` [`number`]** — The frequency-independent electric
+ **`D_conductivity` [ `number` ]** — The frequency-independent electric
conductivity $\\sigma_D$. Default is 0. You can also specify a diagonal
anisotropic conductivity tensor by using the property `D_conductivity_diag`
which takes a `Vector3` to give the $\\sigma_D$ tensor diagonal. See also
[Conductivity](Materials.md#conductivity-and-complex).

+ **`B_conductivity` [`number`]** — The frequency-independent magnetic
+ **`B_conductivity` [ `number` ]** — The frequency-independent magnetic
conductivity $\\sigma_B$. Default is 0. You can also specify a diagonal
anisotropic conductivity tensor by using the property `B_conductivity_diag`
which takes a `Vector3` to give the $\\sigma_B$ tensor diagonal. See also
[Conductivity](Materials.md#conductivity-and-complex).

+ **`chi2` [`number`]** — The nonlinear electric
+ **`chi2` [ `number` ]** — The nonlinear electric
[Pockels](https://en.wikipedia.org/wiki/Pockels_effect) susceptibility
$\\chi^{(2)}$ (quadratic nonlinearity). Default is 0. See also [Nonlinearity](Materials.md#nonlinearity).
This is equivalent to setting `E_chi2`; alternatively, an analogous magnetic
nonlinearity can be specified using `H_chi2`. These are isotropic nonlinearities,
but *diagonal* anisotropic polarizations of the form $\\chi_i^{(2)} E_i^2$ can
be specified with `E_chi2_diag` (which defaults to `[E_chi2,E_chi2,E_chi2]`).

+ **`chi3` [`number`]** — The nonlinear electric
+ **`chi3` [ `number` ]** — The nonlinear electric
[Kerr](https://en.wikipedia.org/wiki/Kerr_effect) susceptibility $\\chi^{(3)}$
(cubic nonlinearity). Default is 0. See also [Nonlinearity](Materials.md#nonlinearity).
This is equivalent to setting `E_chi3`; alternatively, an analogous magnetic nonlinearity
Expand All @@ -391,12 +397,12 @@ def __init__(
`E_chi3_diag` (which defaults to `[E_chi3,E_chi3,E_chi3]`).

+ **`E_susceptibilities` [ list of `Susceptibility` class ]** — List of dispersive
susceptibilities (see below) added to the dielectric constant ε in order to
susceptibilities (see below) added to the dielectric constant $\\varepsilon$ in order to
model material dispersion. Defaults to none (empty list). See also [Material
Dispersion](Materials.md#material-dispersion).

+ **`H_susceptibilities` [ list of `Susceptibility` class ]** — List of dispersive
susceptibilities (see below) added to the permeability μ in order to model
susceptibilities (see below) added to the permeability $\\mu$ in order to model
material dispersion. Defaults to none (empty list). See also [Material
Dispersion](Materials.md#material-dispersion).
"""
Expand Down Expand Up @@ -1688,7 +1694,7 @@ def find_root_deriv(f, tol, x_min, x_max, x_guess=None):
f_memo = memoize(f)

def lazy(x):
return x if isinstance(x, numbers.Number) else x()
return x if isinstance(x, Number) else x()

def pick_bound(which):
def _pb():
Expand Down Expand Up @@ -1730,7 +1736,7 @@ def newton(x, a, b, dx):
):
raise ValueError("failed to bracket the root in find_root_deriv")

if isinstance(a, numbers.Number) and isinstance(b, numbers.Number):
if isinstance(a, Number) and isinstance(b, Number):
is_in_bounds = in_bounds(x, f, df, a, b)
else:
is_in_bounds = in_bounds(x, f, df, x_min, x_max)
Expand Down
Loading