Week 1, Second Task: SSH Model

In [2]:
%run ../code/init_mooc_nb.ipy
Performing the necessary imports.

from __future__ import division, print_function
import numpy as np
import matplotlib
import kwant

import ipywidgets
from IPython.html.widgets import interact
from ipywidgets import StaticInteract, RangeWidget, DropDownWidget
from IPython.display import display_html
from matplotlib import pyplot as plt

import pfaffian as pf
from edx_components import *

Executing 'import ipywidgets' failed.
Executing 'from ipywidgets import StaticInteract, RangeWidget, DropDownWidget' failed.

Press this button to show/hide the code used in the notebook:

Expectations

The SSH-chain consists of a 2-atom basis, which allows us to define sublattices $A$ and $B$. E.g. atom $A$ sits at relative coordinate $x = 0.0$, whereas the $B$ atom sits at relative coordinate $x = 0.5$ in the unit cell.

As we vary the relative strength of the intracell interaction $t_1$ and intercell interaction $t_2$, we expect to observe two regimes. In the $t_1 > t_2$ case, $AB$ dimers will form within each unit cell, leaving no unpaired electrons on the end. In the $t_2 > t_1$ regime, dimers will form across the unit-cell boundaries, and unpaired electrons will remain on the $A$ atom on one side and the $B$ atom on the other side.

So long as sublattice symmetry persists, we expect two degenerate states at zero energy. (Why zero energy, though?) As soon as sublattice symmetry is broken (for example by setting different on-site energies $\mu$ on both sublattices), it's clear the degenerate states will split into a state where the $A$-lattice occupation dies out, and one where the $B$-lattice occupation dies out.

Numerics

We perform a quick Tight-Binding simulation for the SSH-chain model using the PythTB package. While Kwant seems like a powerful tool for transport calculations, it doesn't seem like a TB package at heart. By the "The right tool for the right job" maxim, we opted for PythTB instead.

In [3]:
from pythtb import *

def make_ssh_model(L, t1, t2, mu):
    
    lat = [[1.0]]
    orb = [[0.0],[0.5]]
    ssh_model = tbmodel(1,1, lat, orb)
    
    ssh_model.set_onsite([mu, -mu])# mu != 0 breaks sublattice symmetry
    
    ssh_model.set_hop(t1, 0, 1, [0,]) # Intracell hopping
    ssh_model.set_hop(t2+0.0001, 1, 0, [1,]) # Intercell hopping
    
    ssh_model = ssh_model.cut_piece(L, 0) # Cut a finite chain

    return ssh_model
---------------------------------------------------------------------------
ImportError                               Traceback (most recent call last)
<ipython-input-3-d334574036e3> in <module>()
----> 1 from pythtb import *
      2 
      3 def make_ssh_model(L, t1, t2, mu):
      4 
      5     lat = [[1.0]]

ImportError: No module named pythtb

Some routines for plotting the spectrum and corresponding site occupations side to side. Largely an exact copy from the MOOC source-code.

In [65]:
def plot_spectrum(L, t1, t2, mu, ax):
    spectrum = []
    t2s = np.linspace(0.0, 4.0)
    for _t2 in t2s:
        ssh_model = make_ssh_model(L, t1, _t2, mu)
        evals = ssh_model.solve_one()
        spectrum.append(evals)
    
    ### Set axes    
    ymax = 6.
    ax.set_ylim(-ymax, ymax)
    ax.set_yticks(np.array(np.arange(-ymax, ymax+.1)))
    ax.set_xlim(0.0, 4.0)
    ax.set_xticks(np.arange(5))
    ax.set_xlabel("$t_2/t_1$")
    ax.set_ylabel("$E/t_1$")
    ###
    
    ax.plot(t2s, spectrum, "black")
    ax.plot(np.array([t2, t2]), np.array([-ymax, ymax]), 'b--')

def plot_states(L, t1, t2, mu, ax):
    ssh_model = make_ssh_model(L, t1, t2, mu)
    (evals,evecs) = ssh_model.solve_all(eig_vectors=True)
    ed = ssh_model.get_num_orbitals()/2
    
    ### Set axes
    ax.set_xlim(0, L-1)
    ax.set_xlabel("$x$")
    ax.set_ylabel("$|u|^2 + |v|^2$")
    plt.yticks([])
    plt.xticks(range(0, L, 5))
    ###
    
    ax.plot(np.abs(evecs[ed,0:2*L:2])**2 , 'b-') # A sublattice   
    ax.plot(np.abs(evecs[ed,1:2*L:2])**2 , 'g-') # B sublattice
         
def plot_both(L, t1, t2, mu):
    fig = plt.figure(figsize=(9, 3.5))
    ax1 = fig.add_subplot(1, 2, 1)    
    ax2 = fig.add_subplot(1, 2, 2)    

    plot_states(L, t1, t2, mu,ax2);
    plot_spectrum(L, t1, t2, mu, ax1);
    return fig
    

An interactive plot of the spectrum and occupations as $t_2$ is varied. It is clear the transition from trivial to topological occurs around $t_2 = t_1$. We have plotted the occupations of $A$-lattice electron (blue) and $B$-lattice (green) seperately per unit cell, so it is clear that indeed, in the topological regime, an electron is localized on the left-hand $A$-site, and the other on the right-hand $B$-site.

In [69]:
StaticInteract((lambda t2: plot_both(20, 1.0, t2, 0.0)), 
         t2=RangeWidget(0.0, 4.0, 0.2, name='t2', default=0, show_range=True))
Out[69]:
0.0 t2: 4.0

In the next interactive plot, we play around with sublattice symmetry by introducing opposite on-site energies $\pm \mu$ for $A$ and $B$ sites respectively. It's clear that breaking the symmetry immediately lifts the degeneracy of the edge-electron states as one edge electron becomes unoccupied and spreads over the bulk.

In [72]:
StaticInteract((lambda mu: plot_both(15, 1.0, 1.3, mu)), 
         mu=RangeWidget(0.0, 0.2, 0.01, name='mu', default=0, show_range=True))
Out[72]:
0.0 mu: 0.2