Hello,
While I was looking at the function test_dmrg_excited in test_dmry.py, I noticed the excited states searched by tenpy are all in the same symmetry sector.
I wonder if there is a way to get excited states in other symmetry sectors with tenpy?
Get excited states in different symmetry sectors
Re: Get excited states in different symmetry sectors
Yes: just run DMRG with an initial state in the symmetry sector you're interested in.
DMRG doesn't switch charge sectors, so the charge sector of the final state is determined by your initial state.
DMRG doesn't switch charge sectors, so the charge sector of the final state is determined by your initial state.
Re: Get excited states in different symmetry sectors
Thanks a lot for the reply. I did a few tests, it's exactly as what you said. But I found using single site DMRG gives me wrong results. Can you explain why it is so? See the code below.
The result is
For comparison, using two site DMRG gives
Code: Select all
def test_dmrg_excited(eps=1.e-12):
L, g = 8, 1.3
bc = 'finite'
model_params = dict(L=L, J=1., g=g, bc_MPS=bc, conserve='parity')
M = TFIChain(model_params)
# compare to exact solution
ED = ExactDiag(M)
ED.build_full_H_from_mpo()
ED.full_diagonalization()
# Note: energies sorted by chargesector (first 0), then ascending -> perfect for comparison
print("Exact diag: E[:5] = ", ED.E[:5])
print("Exact diag: (smalles E)[:10] = ", np.sort(ED.E)[:10])
psi_ED = [ED.V.take_slice(i, 'ps*') for i in range(5)]
print("charges : ", [psi.qtotal for psi in psi_ED])
# first DMRG run
psi0 = mps.MPS.from_product_state(M.lat.mps_sites(), [0] * L, bc=bc)
dmrg_pars = {
'N_sweeps_check': 1,
'lanczos_params': {
'reortho': False
},
'trunc_params': {
'chi_max': 100,
'svd_min': 1.e-10
},
'diag_method': 'lanczos',
'combine': True
}
eng0 = dmrg.SingleSiteDMRGEngine(psi0, M, dmrg_pars)
E0, psi0 = eng0.run()
# second DMRG run
# dmrg_pars['orthogonal_to'] = [psi0]
produc_state = [0] * L
produc_state[0] = 1
psi1 = mps.MPS.from_product_state(M.lat.mps_sites(), produc_state, bc=bc)
eng1 = dmrg.SingleSiteDMRGEngine(psi1, M, dmrg_pars)
E1, psi1 = eng1.run()
print("Ground state energy: ", E0, "; First excited state energy: ", E1)
Code: Select all
Exact diag: E[:5] = [-11.78491823 -9.44235849 -8.74371507 -8.13069442 -8.0720393 ]
Exact diag: (smalles E)[:10] = [-11.78491823 -10.92014868 -10.30712804 -9.60848462 -9.44235849
-8.93680885 -8.74371507 -8.34083256 -8.13069442 -8.0720393 ]
charges : [array([0]), array([0]), array([0]), array([0]), array([0])]
Ground state energy: -10.4 ; First excited state energy: -7.8
Code: Select all
Exact diag: E[:5] = [-11.78491823 -9.44235849 -8.74371507 -8.13069442 -8.0720393 ]
Exact diag: (smalles E)[:10] = [-11.78491823 -10.92014868 -10.30712804 -9.60848462 -9.44235849
-8.93680885 -8.74371507 -8.34083256 -8.13069442 -8.0720393 ]
charges : [array([0]), array([0]), array([0]), array([0]), array([0])]
Ground state energy: -11.784918232217056 ; First excited state energy: -10.920148680807984
Re: Get excited states in different symmetry sectors
For single-site DMRG to work you need to enable the "mixer" by setting
I've just released a bugfix version 0.8.4, where I changed the default setting for the
dmrg_params['mixer']=True
, otherwise it cannot grow the bond dimension. Be warned that the default mixer_params
might still disable the mixer too early for larger/more correlated systems.I've just released a bugfix version 0.8.4, where I changed the default setting for the
mixer
paramter to be True for SingleSiteDMRG, such that it turns on the mixer at least initially.