コンテンツにスキップ

ED-02 Gaps

一次元量子スピン系のスピンギャップ

このチュートリアルでは、スパース対角化プログラムを用いて一次元量子スピン系のスピンギャップを計算し、その有限サイズスケーリングを調べます。 反強磁性スピン鎖にとって中心的な問いは、基底状態の上に有限の励起ギャップを持つか、あるいはギャップレスであるかということです。Haldane は、等方的ハイゼンベルク鎖の振る舞いがスピン量子数 SS が整数であるか半整数であるかによって全く異なることを予想しました。これは現在では数値計算と場の理論的な議論の両方によって確固たるものとなっています:整数スピン鎖は一意でギャップを持つ基底状態(「Haldane ギャップ」)を持ち、半整数スピン鎖はギャップレスでべき乗則的に減衰する相関を持ちます(F.D.M. Haldane, Phys. Rev. Lett. 50, 1153 (1983))。有限系は常に離散スペクトルを持つため、この定性的な違いは有限サイズギャップを LL\to\infty に外挿して初めて見えてきます——これがまさに以下で S=1S=1S=1/2S=1/2 について行うことです。

どちらの場合もハミルトニアンは等方的ハイゼンベルク鎖

H=Ji,jSiSj,J=1, H = J \sum_{\langle i,j \rangle} \mathbf{S}_i \cdot \mathbf{S}_j , \qquad J=1 ,

であり、LL サイトの周期鎖上で定義され、局所スピンの大きさ SS のみが異なります。

パラメータ

パラメータ意味
LATTICE周期鎖chain lattice
MODEL量子スピン模型spin
local_S各サイトのスピン量子数1(parm2a)または 1/2(parm2b
J最近接ハイゼンベルク結合1
L鎖長4, 6, 8, 10
CONSERVED_QUANTUMNUMBERSHH をブロック対角化するために用いる対称性Sz
Sz_total対角化を単一の SzS_z セクターに制限する0(一重項セクター)と 1(三重項セクター)

格子

どちらの鎖も ALPS格子ライブラリに内蔵されている周期的な chain lattice を用います。以下は L=6L=6 の場合の模式図です。

    J     J     J     J     J
o-------o-------o-------o-------o-------o
0       1       2       3       4       5
|_______________________________________|
                   J   (bond 5-0, periodic)

手法

Sz=0S_z=0Sz=1S_z=1 のセクターをそれぞれ独立に対角化し、それぞれの最低固有値を取ることで、(はるかに大きい)全スペクトルを探索することなく、一重項基底状態と最低の三重項励起を切り分けることができます。ここで最大のセクター(S=1S=1L=10L=10、次元 89538953)であっても、sparsediag の背後にある Lanczos 反復法で容易に扱えます。各セクターで最低状態のみが必要なので、全対角化は不要であり、はるかにコストもかかります。

スピン1鎖のスピンギャップ

コマンドラインを用いる方法

パラメータファイル parm2a は、4〜10サイトの量子力学的 S=1 鎖について、一重項および三重項セクターでの厳密対角化を設定します。

MODEL="spin"
LATTICE="chain lattice"
CONSERVED_QUANTUMNUMBERS="Sz"
local_S=1
J=1
Sz_total=0
{L=4}
{L=6}
{L=8}
{L=10}
Sz_total=1
{L=4}
{L=6}
{L=8}
{L=10}

パラメータ Sz_total は、守恒量子数 Sz を与えられた値に制限します。模型やその守恒量子数の設定方法についての詳細はモデルライブラリのドキュメントを参照してください。 標準的な一連のコマンドを使い、まず入力パラメータを XML に変換し、続いてアプリケーション sparsediag を実行します。

parameter2xml parm2a
sparsediag --write-xml parm2a.in.xml

ギャップの評価は、出力ファイルを手作業で確認することでも行えますし、Python を使って一連の作業を自動化することもできます。

Python を用いる方法

Python でシミュレーションを設定・実行するには、スクリプト tutorial2a.py を使用します。このスクリプトの最初の部分では、必要なモジュールをインポートし、入力パラメータを Python の辞書のリストとして準備し、入力ファイルを書き出してアプリケーションを実行します。

import pyalps
import numpy as np
import matplotlib.pyplot as plt
import pyalps.pyplot
parms = []
for l in [4, 6, 8, 10]:
    for sz in [0, 1]:
        parms.append({ 
            'LATTICE'                   : "chain lattice", 
            'MODEL'                     : "spin",
            'local_S'                   : 1,
            'J'                         : 1,
            'L'                         : l,
            'CONSERVED_QUANTUMNUMBERS'  : 'Sz',
            'Sz_total'                  : sz
        })
     
input_file = pyalps.writeInputFiles('parm2a',parms)
res = pyalps.runApplication('sparsediag',input_file)

これを実行するには、ターミナルで python tutorial2a.py と入力します。これでコマンドライン版と同じ出力ファイルが得られます。 次に、各システムサイズとスピンセクターについてのスペクトルを読み込みます。

data = pyalps.loadSpectra(pyalps.getResultFiles(prefix='parm2a'))

ギャップを抽出するには、長さのリストと、各 (L,Sz) セクターにおける最小エネルギーを格納する Python 辞書を作るために、数行の Python コードを書く必要があります。

lengths = []
min_energies = {}
for sim in data:
    l = int(sim[0].props['L'])
    if l not in lengths: lengths.append(l)
    sz = int(sim[0].props['Sz_total'])
    all_energies = []
    for sec in sim:
        all_energies += list(sec.y)
    min_energies[(l,sz)]= np.min(all_energies)

最後に、ギャップを 1/L の関数としてプロットし、表示します。

gapplot = pyalps.DataSet()
gapplot.x = 1./np.sort(lengths)
gapplot.y = [min_energies[(l,1)] -min_energies[(l,0)] for l in np.sort(lengths)]  
gapplot.props['xlabel']='$1/L$'
gapplot.props['ylabel']='Triplet gap $\Delta/J$'
gapplot.props['label']='S=1'

plt.figure()
pyalps.plot.plot(gapplot)
plt.legend()
plt.xlim(0,0.25)
plt.ylim(0,1.0)
plt.show()

スピン1/2鎖のスピンギャップ

スピン1鎖について外挿したギャップを、スピン1/2鎖のものと比較してみましょう。そのためには、local_S=1 を local_S=0.5 に変えてシミュレーションを実行するだけです(ただし名前は parm2b にします)。パラメータファイル parm2b は、それ以外は parm2a と全く同じです。

MODEL="spin"
LATTICE="chain lattice"
CONSERVED_QUANTUMNUMBERS="Sz"
local_S=1/2
J=1
Sz_total=0
{L=4}
{L=6}
{L=8}
{L=10}
Sz_total=1
{L=4}
{L=6}
{L=8}
{L=10}

Python スクリプトは tutorial2b.py です。

両方の系を1つの図にまとめる

最初の2つのチュートリアルを実行した後、Python スクリプト tutorial2c.py を実行すると、両方のギャップを1つの図にまとめて表示できます。 スピン1/2とスピン1の両方について、格子サイズの関数としてのギャップを次の図に示します。

出力データ

下の表は、2つのパラメータファイルから得られる厳密な三重項ギャップ Δ(L)=E0(Sz=1)E0(Sz=0)\Delta(L)=E_0(S_z=1)-E_0(S_z=0) を、自分の実行結果と比較するための参考として示したものです。

LL1/L1/Lギャップ Δ/J\Delta/J、S=1ギャップ Δ/J\Delta/J、S=1/2
40.2501.00001.0000
60.1670.72060.6847
80.1250.59360.5227
100.1000.52480.4232

S=1 のギャップは頭打ちになりつつあり、(例えば 1/L1/L に対する2次フィットにより)文献にある Haldane ギャップの推定値 Δ0.41J\Delta_\infty \approx 0.41\,J に近い有限の値へと外挿されます。一方 S=1/2 のギャップは減少し続けており、ゼロへ外挿されることと矛盾しません——これはギャップレス鎖の特徴です。

まとめ

同じ最近接反強磁性ハイゼンベルク結合のもとで、S=1 鎖は有限の励起ギャップへと外挿され、S=1/2 鎖はゼロへと外挿されます。これは、厳密に対角化できるほど小さな鎖上で Haldane 予想を直接確認するものです。

問題

  • 無限系に対して外挿されるギャップの値はいくらですか。
  • なぜ S=1/2 鎖と S=1 鎖は異なる振る舞いを示すのでしょうか。
  • 上表の S=1 のデータに対して、2次フィット Δ(L)=Δ+a/L+b/L2\Delta(L) = \Delta_\infty + a/L + b/L^2 を試してください。外挿された Δ\Delta_\infty は文献値 0.41J\approx 0.41 J にどれだけ近いですか。