meanas/examples/bloch.py

111 lines
2.9 KiB
Python
Raw Normal View History

2019-08-04 14:13:51 -07:00
import numpy, scipy, gridlock, meanas
from meanas.fdfd import bloch
2017-12-21 20:11:42 -08:00
from numpy.linalg import norm
import logging
2019-07-09 20:13:49 -07:00
from pathlib import Path
2017-12-21 20:11:42 -08:00
2022-10-04 12:27:10 -07:00
2017-12-21 20:11:42 -08:00
logging.basicConfig(level=logging.DEBUG)
logger = logging.getLogger(__name__)
2022-10-04 12:27:10 -07:00
WISDOM_FILEPATH = Path.home() / '.local/share/pyfftw/wisdom.pickle'
2017-12-21 20:11:42 -08:00
2019-07-09 20:13:49 -07:00
def pyfftw_save_wisdom(path):
2022-10-04 12:27:10 -07:00
path = Path(path)
2019-07-09 20:13:49 -07:00
try:
import pyfftw
import pickle
except ImportError as e:
pass
path.parent.mkdir(parents=True, exist_ok=True)
2023-05-23 12:56:48 -07:00
wisdom = pyfftw.export_wisdom()
2019-07-09 20:13:49 -07:00
with open(path, 'wb') as f:
pickle.dump(wisdom, f)
def pyfftw_load_wisdom(path):
2022-10-04 12:27:10 -07:00
path = Path(path)
2019-07-09 20:13:49 -07:00
try:
import pyfftw
import pickle
except ImportError as e:
pass
if path.exists():
2019-07-09 20:13:49 -07:00
with open(path, 'rb') as f:
wisdom = pickle.load(f)
pyfftw.import_wisdom(wisdom)
2019-07-09 20:13:49 -07:00
logger.info('Drawing grid...')
2017-12-21 20:11:42 -08:00
dx = 40
x_period = 400
y_period = z_period = 2000
2023-05-23 12:56:48 -07:00
g = gridlock.Grid([
numpy.arange(-x_period/2, x_period/2, dx),
numpy.arange(-1000, 1000, dx),
numpy.arange(-1000, 1000, dx)],
shifts=numpy.array([[0,0,0]]),
periodic=True,
)
2022-10-04 12:29:11 -07:00
gdata = g.allocate(1.445**2)
2017-12-21 20:11:42 -08:00
2022-10-04 12:29:11 -07:00
g.draw_cuboid(gdata, [0,0,0], [200e8, 220, 220], foreground=3.47**2)
2017-12-21 20:11:42 -08:00
#x_period = y_period = z_period = 13000
#g = gridlock.Grid([numpy.arange(3), ]*3,
# shifts=numpy.array([[0, 0, 0]]),
# initial=2.0**2,
# periodic=True)
g2 = g.copy()
g2.shifts = numpy.zeros((6,3))
2022-10-04 12:29:11 -07:00
g2data = g2.allocate(0)
2017-12-21 20:11:42 -08:00
2022-10-04 12:29:11 -07:00
epsilon = [gdata[0],] * 3
2018-01-08 16:16:26 -08:00
reciprocal_lattice = numpy.diag(1000/numpy.array([x_period, y_period, z_period])) #cols are vectors
2017-12-21 20:11:42 -08:00
2019-07-09 20:13:49 -07:00
pyfftw_load_wisdom(WISDOM_FILEPATH)
2017-12-21 20:11:42 -08:00
#print('Finding k at 1550nm')
2018-01-08 16:16:26 -08:00
#k, f = bloch.find_k(frequency=1000/1550,
# tolerance=(1000 * (1/1550 - 1/1551)),
2017-12-21 20:11:42 -08:00
# direction=[1, 0, 0],
# G_matrix=reciprocal_lattice,
# epsilon=epsilon,
# band=0)
#
2023-05-23 12:56:48 -07:00
#kf = norm(reciprocal_lattice @ k) / f)
#print(f'{k=}, {f=}, 1/f={1/f}, k/f={kf}')
2017-12-21 20:11:42 -08:00
2019-07-09 20:13:49 -07:00
logger.info('Finding f at [0.25, 0, 0]')
2017-12-21 20:11:42 -08:00
for k0x in [.25]:
k0 = numpy.array([k0x, 0, 0])
kmag = norm(reciprocal_lattice @ k0)
2018-01-08 16:16:26 -08:00
tolerance = (1000/1550) * 1e-4/1.5 # df = f * dn_eff / n
2023-05-23 12:56:48 -07:00
logger.info(f'tolerance {tolerance}')
2017-12-21 20:11:42 -08:00
2018-01-08 16:16:26 -08:00
n, v = bloch.eigsolve(4, k0, G_matrix=reciprocal_lattice, epsilon=epsilon, tolerance=tolerance**2)
2017-12-21 20:11:42 -08:00
v2e = bloch.hmn_2_exyz(k0, G_matrix=reciprocal_lattice, epsilon=epsilon)
v2h = bloch.hmn_2_hxyz(k0, G_matrix=reciprocal_lattice, epsilon=epsilon)
ki = bloch.generate_kmn(k0, reciprocal_lattice, g.shape)
z = 0
e = v2e(v[0])
for i in range(3):
2022-10-04 12:29:11 -07:00
g2data[i] += numpy.real(e[i])
g2data[i+3] += numpy.imag(e[i])
2017-12-21 20:11:42 -08:00
f = numpy.sqrt(numpy.real(numpy.abs(n))) # TODO
2023-05-23 12:56:48 -07:00
print(f'{k0x=:3g}')
print(f'eigval={n}')
print(f'{f=}')
2017-12-21 20:11:42 -08:00
n_eff = norm(reciprocal_lattice @ k0) / f
2023-05-23 12:56:48 -07:00
print(f'kmag/f = n_eff = {n_eff}')
print(f'wl={1/f}\n')
2017-12-21 20:11:42 -08:00
2019-07-09 20:13:49 -07:00
pyfftw_save_wisdom(WISDOM_FILEPATH)