Skip to content
Snippets Groups Projects
Commit 9a07efd5 authored by Anton Akhmerov's avatar Anton Akhmerov Committed by Christoph Groth
Browse files

move modes calculation out of the solvers

parent 0edb95b4
Branches
Tags
No related merge requests found
......@@ -168,27 +168,16 @@ class SparseSolver(object):
lead_info = []
for leadnum, interface in enumerate(sys.lead_interfaces):
lead = sys.leads[leadnum]
if isinstance(lead, system.InfiniteSystem) and not force_realspace:
h = lead.slice_hamiltonian(args=args)
if check_hermiticity:
if not np.allclose(h, h.T.conj(), rtol=1e-13):
msg = "Lead number {0} has a non-Hermitian " \
"slice Hamiltonian."
raise ValueError(msg.format(leadnum))
h -= energy * np.identity(h.shape[0])
v = lead.inter_slice_hopping(args=args)
modes = physics.modes(h, v)
if hasattr(lead, 'modes') and not force_realspace:
modes = lead.modes(energy, args=args)
lead_info.append(modes)
u, ulinv, nprop, svd_v = modes
# Note: np.any(v) returns (at least from NumPy 1.6.1 -
# 1.8-devel) False if v is purely imaginary
if not (np.any(v.real) or np.any(v.imag)):
if len(u) == 0:
# See comment about zero-shaped sparse matrices at the top.
rhs.append(np.zeros((lhs.shape[1], 0)))
continue
u, ulinv, nprop, svd_v = modes
if svd_v is not None:
svd_v = svd_v.T.conj()
......
......@@ -68,7 +68,8 @@ class FiniteSystem(System):
Instance Variables
------------------
leads : sequence of lead objects
Each lead object has to provide a method ``self_energy(energy, args)``.
Each lead object has to provide a method ``self_energy(energy, args)``
or ``modes(energy, args)`` which calculates its self-energy or modes.
lead_interfaces : sequence of sequences of integers
Each sub-sequence contains the indices of the system sites to which the
lead is connected.
......@@ -145,6 +146,20 @@ class InfiniteSystem(System):
return self.hamiltonian_submatrix(slice_sites, neighbor_sites,
sparse=sparse, args=args)
def modes(self, energy, args=()):
"""Return self-energy of a lead.
The returned matrix has the shape (n, n), where n is
``sum(self.num_orbitals(i) for i in range(self.slice_size))``.
"""
ham = self.slice_hamiltonian(args=args)
shape = ham.shape
assert len(shape) == 2
assert shape[0] == shape[1]
# Subtract energy from the diagonal.
ham.flat[::ham.shape[0] + 1] -= energy
return physics.modes(ham, self.inter_slice_hopping(args=args))
def self_energy(self, energy, args=()):
"""Return self-energy of a lead.
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment