ITensor Support Q&A - Recent questions and answers
http://itensor.org/support/qa
Powered by Question2AnswerAnswered: Thermal state missing/null link index
http://itensor.org/support/2637/thermal-state-missing-null-link-index?show=2645#a2645
<p>Hi,</p>
<p>For now, you need to make sure your MPS always has link indices, even if they are trivial.</p>
<p>In the future, we would like to relax this constraint, since it is kind of annoying, but it would require some work to make sure all of the internal MPS code can properly handle the case where there are no link indices. This is a good example of where the current design is too strict, and a good reminder that we should loosen the restriction.</p>
<p>-Matt</p>
http://itensor.org/support/2637/thermal-state-missing-null-link-index?show=2645#a2645Wed, 28 Oct 2020 20:46:28 +0000Error in the energy
http://itensor.org/support/2643/error-in-the-energy
<p>I'm just wondering if it's possible to extract the error in the energy one gets from running a DMRG calculation. Obviously, there isn't a statistical error bar like there would be in a Monte Carlo simulation. But, is it known how truncation errors in the eigenvalues of the reduced density matrix translate to errors in the energy?</p>
http://itensor.org/support/2643/error-in-the-energyWed, 28 Oct 2020 18:56:26 +0000Answered: Construction of Matrix product density operator
http://itensor.org/support/2641/construction-of-matrix-product-density-operator?show=2642#a2642
<p>Hi, good question but the important thing to know is that basically the MPS and MPO classes in ITensor are essentially just arrays of ITensors. The only details beyond them just being arrays are that they "remember" their orthogonality center (if they have one) and they have some associated functions that expect those types (MPS, MPO) to be passed.</p>
<p>But you can always put any collection of ITensors into an array and pass this array around, or store this array in a custom type (MPDO, say) then define analogous functions or operations on it as we have for MPS and MPO.</p>
<p>Finally, an MPDO is structurally equivalent to an MPO, correct? If so you could just repurpose the ITensor MPO type for your work. Or are you referring to the network I know as a "locally purified state" which looks more like two MPO's contracted together? </p>
<p>Best regards,<br>
Miles</p>
http://itensor.org/support/2641/construction-of-matrix-product-density-operator?show=2642#a2642Wed, 28 Oct 2020 13:53:47 +0000Answered: Exact MPO option for the julia version
http://itensor.org/support/2636/exact-mpo-option-for-the-julia-version?show=2640#a2640
<p>Hi, good question but we don't offer the "Exact" back-end for AutoMPO right now in the Julia version. We just haven't ported it over, since the other backend (which I guess could be called "Compressing" or "SVD") is generally more useful as it can handle a much wider set of inputs.</p>
<p>However, it's important to know that the current backend is very accurate. It does make some approximations but these are basically to truncate singular values of certain matrices going into the MPO which are below 1E-13, so machine precision zero essentially.</p>
<p>Finally, you can test the quality of the MPO that is produced by computing matrix elements with product state MPS. You can use the <code>productMPS</code> function to make these MPS, then the <code>inner(psi,H,phi)</code> function to compute the matrix elements, to check whether they match the exact result you expect for your Hamiltonian.</p>
<p>Please let me know if you have any follow up questions about any of this.</p>
<p>Miles</p>
http://itensor.org/support/2636/exact-mpo-option-for-the-julia-version?show=2640#a2640Tue, 27 Oct 2020 20:25:57 +0000Getting "Index does not contain given QN block" error
http://itensor.org/support/2638/getting-index-does-not-contain-given-qn-block-error
<p>Hi!<br>
I'm using AutoMPO to implement the following hamiltonian. Here is a snippet of my code</p>
<pre><code>int N = 12;
int Nc = N/2;
auto ampo = AutoMPO(sites);
auto Npart = N;
auto t1 = 1;
auto t2 = 0.5;
auto sites = Electron(N);
for(int b = 1; b < N; ++b)
{
ampo += t1,"Cdagup",b+1,"Cup",b;
ampo += -t1,"Cdagdn",b+1,"Cdn",b;
ampo += -t1,"Cdagup",b,"Cup",b+1;
ampo += t1,"Cdagdn",b,"Cdn",b+1;
}
ampo += t2,"Nup",Nc;
ampo += t2,"Ndn",Nc;
ampo += t2,"Cdagup",Nc,"Cdn",Nc;
ampo += t2,"Cdagdn",Nc,"Cup",Nc;
auto H = toMPO(ampo);
</code></pre>
<p>When I run my code I get the following error: "Index does not contain given QN block". When I remove the part containing the terms with 't2' the code runs fine. Is this due to some bug in AutoMPO or am I making some mistake when I do this? Is there anyway to get around this problem?</p>
<p>Best Regards<br>
NIkhil</p>
http://itensor.org/support/2638/getting-index-does-not-contain-given-qn-block-errorTue, 27 Oct 2020 11:51:34 +0000Answered: Spinless Fermion correlator in Julia
http://itensor.org/support/2629/spinless-fermion-correlator-in-julia?show=2633#a2633
<p>Hi, you should be able to follow essentially the same code as: <a rel="nofollow" href="http://www.itensor.org/docs.cgi?vers=cppv3&page=formulas/spinless_correlator_mps">http://www.itensor.org/docs.cgi?vers=cppv3&page=formulas/spinless_correlator_mps</a></p>
<p>Yes, you can use <code>commonind(psi[i],psi[i-1])</code> or <code>linkind(psi, i-1)</code> to get the left link index of site <code>i</code>.</p>
http://itensor.org/support/2629/spinless-fermion-correlator-in-julia?show=2633#a2633Thu, 22 Oct 2020 13:58:23 +0000How to calculate string operator in ITensor2?
http://itensor.org/support/2632/how-to-calculate-string-operator-in-itensor2
<p>Hi ITensor team,<br>
Thanks for your wonderful software ! I want to calculate Haldane string operator correlation function, so I want to define string operator, for example <\prod<em>{n<I}exp(I\pi S</em>{n}^{z})S^{z}_{I}>.if I have string operator, then I can calculate correlation function as spin correlation function. But I don't know how to exponential operator Sz(maybe MPO). my naive partial code as follow:</p>
<p>auto phi1=expHermitian(sites.op("Sz",1),PI<em>Cplx_i);<br>
auto phi2=expHermitian(sites.op("Sz",1),PI</em>Cplx_i);</p>
<p>for(int n = 2; n < N/4; ++n)<br>
{<br>
phi1 <em>=expHermitian(sites.op("Sz",n),PI</em>Cplx_i);<br>
print(phi1);<br>
}<br>
auto Ss1 = phi1*sites.op("Sz",N/4);</p>
<p>for(int n = 2; n < 3<em>N/4; ++n)<br>
{<br>
phi2 *=expHermitian(sites.op("Sz",n),PI</em>Cplx_i);<br>
}<br>
auto Ss2 = phi2*sites.op("Sz",3*N/4);</p>
<p>Ss1 and Ss2 is string operator at N/4 and 3*N/4. BUT this code does't work. Please help me to check. Thank you !</p>
http://itensor.org/support/2632/how-to-calculate-string-operator-in-itensor2Thu, 22 Oct 2020 13:21:57 +0000Answered: The leading a few eigenvalues with arnoldi
http://itensor.org/support/2628/the-leading-a-few-eigenvalues-with-arnoldi?show=2630#a2630
<p>Hi, this is a known problem with our Arnoldi implementation. I've suggested a workaround here: <a rel="nofollow" href="https://github.com/ITensor/ITensor/issues/360">https://github.com/ITensor/ITensor/issues/360</a></p>
<p>You could also consider using an external library like Arpack. Unfortunately, we don't have the time to debug the Arnoldi code in the near future.</p>
http://itensor.org/support/2628/the-leading-a-few-eigenvalues-with-arnoldi?show=2630#a2630Wed, 21 Oct 2020 21:12:32 +0000Misunderstanding about C/A operators in electron model
http://itensor.org/support/2626/misunderstanding-about-c-a-operators-in-electron-model
<p>Hi ITensor Support,</p>
<p>I am trying to construct and extended Hubbard model Hamiltonian with next-nearest-neighbour hopping but I am having some problems with the A/C operators while using the autoMPO functions.</p>
<p>As a minimal example, I have just considered the usual fermion hopping term </p>
<p>$$ H = - t_0 \sum_{i, s} c_{i, s}^\dagger c_{i+1,s} + c_{i+1, s}^\dagger c_{i,s} $$</p>
<p>I have represented this three different ways using autoMPO: <br>
-1st I just used the A operators without the Jordan-Wigner F operator (which I know should be wrong!)<br>
-2nd I used the C operators as is standard<br>
-3rd I used the A operators with the Jordan-Wigner F operators (this should be the same as above)</p>
<pre><code>int L = 4;
double t0 = 5;
//Set arguments
auto args = Args("Cutoff=",1E-15,"MaxDim=",5000);
//Initialise System
auto sites = Electron(L, {"ConserveQNs=",false});
// Build Evolution Operators
auto ampo = AutoMPO(sites);
auto ampo2 = AutoMPO(sites);
auto ampo3 = AutoMPO(sites);
//Effective Hamiltonian
//NN Hopping
for(int j = 1; j < L; ++j)
{
int s1 = j;
int s2 = j + 1;
ampo += (-t0) , "Adagup", s1, "Aup", s2;
ampo += (-t0) , "Adagup", s2, "Aup", s1;
ampo += (-t0) , "Adagdn", s1, "Adn", s2;
ampo += (-t0) , "Adagdn", s2, "Adn", s1;
ampo2 += (-t0) , "Cdagup", s1, "Cup", s2;
ampo2 += (-t0) , "Cdagup", s2, "Cup", s1;
ampo2 += (-t0) , "Cdagdn", s1, "Cdn", s2;
ampo2 += (-t0) , "Cdagdn", s2, "Cdn", s1;
ampo3 += (-t0) , "Adagup", s1, "F", s1, "Aup", s2;
ampo3 += -(-t0) , "Aup", s1,"F", s1, "Adagup", s2;
ampo3 += (-t0) , "Adagdn", s1, "F", s1+1, "Adn", s2;
ampo3 += -(-t0) , "Adn", s1,"F", s1+1, "Adagdn", s2;
}
</code></pre>
<p>I then compute the hopping amplitude between a state with a single spin down on the 2nd site and a single spin down on the 3rd site. By hand I get the following results:</p>
<p>$$ <br>
|\psi_0 \rangle = c_{2, \downarrow}^\dagger |0\rangle, \ |\psi_1 \rangle = c_{3, \downarrow}^\dagger |0\rangle, \ \langle \psi_1 |H|\psi_0 \rangle = -t_0 <br>
$$</p>
<p>However, performing the same thing in ITensor (with t_0 = 5) using </p>
<pre><code>auto Ham1 = toMPO(ampo, {"ConserveQNs", false});
auto Ham2 = toMPO(ampo2, {"ConserveQNs", false});
auto Ham3 = toMPO(ampo3, {"ConserveQNs", false});
auto states0 = InitState(sites);
states0.set(2, "Dn");
auto psi0 = MPS(states0);
psi0.orthogonalize();
psi0.normalize();
auto states1 = InitState(sites);
states1.set(3, "Dn");
auto psi1 = MPS(states1);
psi1.orthogonalize();
psi1.normalize();
cout << "Initial State Built" << endl;
auto test1 = innerC(psi1, Ham1, psi0);
auto test2 = innerC(psi1, Ham2, psi0);
auto test3 = innerC(psi1, Ham3, psi0);
Print(test1);
Print(test2);
Print(test3);
</code></pre>
<p>I get:<br>
test1 = (-5, 0)<br>
test2 = (5, 0)<br>
test3 = (5, 0)</p>
<p>Can you understand why these calculations are not agreeing with the theory? I have also tested these results against some exact diagonalisation calculations which agrees with the theory so I am rather confused. I'm sure I have just misunderstood something. I am hoping that by sorting out this bit I might be able to get my full model working.</p>
<p>Many thanks,<br>
Cameron</p>
http://itensor.org/support/2626/misunderstanding-about-c-a-operators-in-electron-modelTue, 20 Oct 2020 09:25:40 +0000Answered: Issue with size of the vector in large bond dimension
http://itensor.org/support/2604/issue-with-size-of-the-vector-in-large-bond-dimension?show=2624#a2624
<p>Please see discussion above. This issue might be now fixed in the latest v3 branch of ITensor, following a recent PR #369 (<a rel="nofollow" href="https://github.com/ITensor/ITensor/pull/369).">https://github.com/ITensor/ITensor/pull/369).</a></p>
<p>However, also note that ITensor DMRG is not guaranteed to work at a given, predetermined large bond dimension, as the reachable bond dimension depends on many details of the code, the system being studied, and the user's software and hardware configuration (size of Hamiltonian MPO, degree of block-sparsity, behavior of memory allocator on user's individual platform and operating system, version of BLAS used, etc.). But we are of course happy to accept fixes and PRs which allow ITensor DMRG to reach larger bond dimensions.</p>
<p>Finally, one trick you might want to try to reach larger bond dimensions is to make separate MPOs for different kinds of terms in your Hamiltonian. For example, you might make one MPO which just has the terms that are local to individual 2d columns, and another MPO that is just the intra-column terms. This approach is not guaranteed to help with memory usage, and often has a bigger impact on time rather than memory, but could still help with things like allowing the code to allocate smaller temporary memory vectors one at a time rather than simultaneously and thereby delay running out of memory.</p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2604/issue-with-size-of-the-vector-in-large-bond-dimension?show=2624#a2624Sat, 17 Oct 2020 16:32:15 +0000Answered: Overlap between two MPS after time evolution
http://itensor.org/support/2591/overlap-between-two-mps-after-time-evolution?show=2618#a2618
<p>(Please see above discussion.)</p>
http://itensor.org/support/2591/overlap-between-two-mps-after-time-evolution?show=2618#a2618Wed, 14 Oct 2020 15:46:14 +0000Answered: How are hopping terms in the Hamiltonian stored in memory? Do they use a lot more memory?
http://itensor.org/support/2594/hopping-terms-hamiltonian-stored-memory-they-use-more-memory?show=2614#a2614
<p>Hi Sujay,<br>
The short version of the answer is that adding individual Hamiltonian terms in an MPO only require the bond dimension of the MPO to be increased by 1. Here by a "term" what is meant is a product of two local operators, such as <code>Sz_1 Sz_7</code>. The operator <code>S+_1 S-_7</code> would be a different term.</p>
<p>On the other hand, translation-invariant terms such as <code>\sum_j Sz_j Sz_j+1</code> also only require the MPO bond dimension to increase by 1, not by N-1 even though this sum contains N-1 terms for a length N system.</p>
<p>So if one starts out with an MPO encoding a sum of local terms, then wants to add the term <code>Sz_1 Sz_N</code> to it, the MPO dimension only has to increase by 1.</p>
<p>All of these comments above are referring to an MPO for an open-boundary, finite system.</p>
<p>Though one can in principle construct and talk about periodic MPOs, the ITensor AutoMPO system does not support making them and the ITensor DMRG code does not accept them as input. This is mostly because periodic MPS have a number of unsolved technical issues that makes them much less useful than either finite or infinite MPS.</p>
<p>For more reading about construction of Hamiltonian MPOs you can see the following papers:<br>
<a rel="nofollow" href="https://arxiv.org/abs/0708.1221">https://arxiv.org/abs/0708.1221</a><br>
<a rel="nofollow" href="https://arxiv.org/abs/1611.02498">https://arxiv.org/abs/1611.02498</a></p>
<p>Miles</p>
http://itensor.org/support/2594/hopping-terms-hamiltonian-stored-memory-they-use-more-memory?show=2614#a2614Tue, 13 Oct 2020 18:58:20 +0000Answered: Bug report in localop.h
http://itensor.org/support/2590/bug-report-in-localop-h?show=2611#a2611
<p>Thank you! I just fixed this in the latest version 3.1.4 based on your report</p>
http://itensor.org/support/2590/bug-report-in-localop-h?show=2611#a2611Mon, 12 Oct 2020 18:12:35 +0000Answered: Sharing a code for the iTDVP?
http://itensor.org/support/2595/sharing-a-code-for-the-itdvp?show=2605#a2605
<p>Hi Yantao,<br>
Thanks for pointing this out! I just added it to the Codes page of the website (C++ part of the codes page of course). Please let me know if you would like to alter the description text, and I can easily change it for you or you can send a pull request since the ITensor.org website is itself open-source.</p>
<p>Appreciate your contribution -</p>
<p>Miles</p>
http://itensor.org/support/2595/sharing-a-code-for-the-itdvp?show=2605#a2605Sun, 11 Oct 2020 20:15:45 +0000Answered: How can I converge to a continuum harmonic trap ground state?
http://itensor.org/support/2579/how-can-i-converge-to-a-continuum-harmonic-trap-ground-state?show=2597#a2597
<p>(Please see the discussion above.)</p>
http://itensor.org/support/2579/how-can-i-converge-to-a-continuum-harmonic-trap-ground-state?show=2597#a2597Fri, 09 Oct 2020 18:22:50 +0000Is there some built-in generalization of KrylovKit.eigsolve that optimizes over multiple input vectors?
http://itensor.org/support/2593/generalization-krylovkit-eigsolve-optimizes-multiple-vectors
<p>I know that the KrylovKit.eigsolve Julia function can find a vector @@x@@ to maximize or minimize @@x^\dagger Ax@@ for a fixed matrix @@M@@. We can think of this in index notation as @@M_{\alpha\beta}x^\alpha\overline{x}^\beta@@, where the bar denotes complex conjugation.</p>
<p>What I am wondering is: does some common package in Julia have a built-in generalization of this method that optimizes over multiple input vectors? For instance, is there a built-in function that finds vectors @@x@@ and @@y@@ to maximize or minimize @@M_{\alpha\beta\gamma\delta}x^\alpha\overline{x}^\beta y^\gamma\overline{y}^\delta@@?</p>
<p>In case you're wondering why I'm asking, basically I am wondering whether it is possible to do a single optimization step over two non-adjacent sites in a way that keeps them unliked, because if you just multiply the two tensors together and then optimize that, then it will introduce a link between those sites. Basically I want to just do this step once in a while to see whether it is possible to fix some problems with my trial Schwinger model (as I have already discussed in some other questions on this website).</p>
http://itensor.org/support/2593/generalization-krylovkit-eigsolve-optimizes-multiple-vectorsFri, 09 Oct 2020 14:25:18 +0000Answered: How do I distinguish between right moving and left moving fermions in ITensor?
http://itensor.org/support/2577/distinguish-between-right-moving-moving-fermions-itensor?show=2587#a2587
<p>Thanks for the extra info above.</p>
<p>So the easiest way to do this with the setup available in ITensor is to define (in your head, more so than in the code) the odd numbered sites to be "L" fermions and the even numbered sites to be "R" fermions. Then this choice is enforced by how you construct the Hamiltonian, such as only inputting hopping terms which connect even to even or odd to odd sites.</p>
<p>Does that approach seem clear to you? Note that converging this setup in DMRG may become a bit harder because two-site DMRG becomes effectively one-site DMRG, but you can overcome this with a good choice of initial state and the use of the noise term.</p>
<p>In the Julia version of ITensor, we offer some more customizability of operators, as used by the AutoMPO system. So there you can introduce custom fermionic operator types and it would be possible to put the L and R fermions on the same site (making dimension 4 site, sort of like in the Hubbard model but with L,R taking the place of spin).</p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2577/distinguish-between-right-moving-moving-fermions-itensor?show=2587#a2587Tue, 06 Oct 2020 20:57:40 +0000Answered: Question of producing a product signlet state and measuring it.
http://itensor.org/support/2566/question-producing-product-signlet-state-and-measuring-it?show=2580#a2580
<p>(See answer in comments above.)</p>
http://itensor.org/support/2566/question-producing-product-signlet-state-and-measuring-it?show=2580#a2580Sat, 03 Oct 2020 16:10:07 +0000Answered: How to define a new Class for particle like "Parafermions"?
http://itensor.org/support/2569/how-to-define-a-new-class-for-particle-like-parafermions?show=2578#a2578
<p>Hi Javad,<br>
Thanks for the question. Indeed we had designed the site set system for custom cases like parafermions.</p>
<p>Though we have not advertised it very much in the documentation or website, the ITensor library code actually includes a file "mps/sites/Z3.h" which defines a site set called Z3 (made out of a site type Z3Site) which implements Z3 parafermions. You could modify that code fairly straightforwardly to do ZN parafermions.</p>
<p>Here is a link to that code:<br>
<a rel="nofollow" href="https://github.com/ITensor/ITensor/blob/v3/itensor/mps/sites/Z3.h">https://github.com/ITensor/ITensor/blob/v3/itensor/mps/sites/Z3.h</a></p>
<p>One thing to note is that the definition of the Tau and Sig (tau and sigma) operators may be flipped from the one you are using, since these conventions differ from paper to paper involving parafermions.</p>
<p>Another very crucial thing to note is that these sites and operators are parafermionic only in a <em>local</em> sense. To properly implement Hamiltonian terms which involve operators acting beyond nearest-neighbor, it's crucial to include non-local strings of "Tau" or "TauDag" operators connecting the interaction operators. This is analogous to how fermions must be implemented using Jordan-Wigner string in ITensor currently.</p>
<p>Finally, note that this same issue about "Tau" string means that the AutoMPO system cannot currently make non-local parafermion Hamiltonians for you. You will need to make a custom Hamiltonian MPO for that. Ideally we are working on a system that will automate all this in the Julia version of ITensor, but I wouldn't expect it to handle parafermions automatically until sometime in late 2021 most likely.</p>
<p>Best regards,<br>
Miles</p>
http://itensor.org/support/2569/how-to-define-a-new-class-for-particle-like-parafermions?show=2578#a2578Thu, 01 Oct 2020 19:41:17 +0000Answered: SVD an ITensor with QN in Julia?
http://itensor.org/support/2560/svd-an-itensor-with-qn-in-julia?show=2565#a2565
<p>Hi Jin,<br>
Thanks for the question. So I think I see the possible issue: the <code>qn</code> function is defined as the "bare" QN which is the one you see printed when you do <code>@show s</code> say, times the arrow direction of the Index. The direction <code>ITensors.Out</code> corresponds to a multiplication of +1, so no change to the bare QN and you see the one printed. But if the direction is <code>ITensors.In</code>, then it multiples the QN by -1 (effectively) which really means to compute the additive inverse of the QN.</p>
<p>The other thing happening here is that your QN's are defined modulo 5; is that intentional? So since you put a modulus value of 5, the additive inverse of 1 modulo 5 is 4 and so for the case where the direction is <code>ITensors.In</code> you are getting the inverse of the bare QN, hence QN("N",4,5). (The "bare" QN in your case is QN("N",1,5) for subspace number 2.)</p>
<p>I don't think any of this is a bug, but it does raise a potential issue we should think about which is whether we should print the total QN (direction times bare QN, as returned by the <code>qn</code> function) rather than just the bare QN when printing an Index. We will think about it.</p>
<p>Regarding the name space conflict for In and Out, it is unfortunate which is why we don't export those values from ITensors.jl. Are you ok with just writing <code>ITensors.In</code> and <code>ITensors.Out</code> ? In a lot of ITensor code it's not required to work with arrows anyway; usually you obtain an In arrow Index by just taking the conjugate of an Out arrow Index using the function <code>dag</code>.</p>
<p>Miles</p>
http://itensor.org/support/2560/svd-an-itensor-with-qn-in-julia?show=2565#a2565Tue, 29 Sep 2020 02:40:49 +0000Answered: Can ITensor calculate 2D Heisenberg model real-time correlation function?
http://itensor.org/support/2558/itensor-calculate-heisenberg-model-correlation-function?show=2559#a2559
<p>Hi, thanks for the question. I think the core of your question is: what are the best ways to use ITensor to time-evolve systems which don't have nearest-neighbor interactions (in a 1D, MPS path order sense, which includes 2D systems).</p>
<p>To understand all of these methods, I'd recommend the review article by Paeckel:<br>
<a rel="nofollow" href="https://arxiv.org/abs/1901.05824">https://arxiv.org/abs/1901.05824</a><br>
as well as some of the material adapted from it on the tensornetwork.org website:<br>
<a rel="nofollow" href="http://tensornetwork.org/mps/algorithms/timeevo/">http://tensornetwork.org/mps/algorithms/timeevo/</a></p>
<p>There are three main methods available in connection with ITensor, and let me briefly list the pros and cons:</p>
<ol>
<li><p>using an MPO representation of the time evolution operator U=exp(-i tau H):</p>
<p>Pros: it is easy to set this up using AutoMPO and the toExpH function, so it is good for testing the other methods too</p>
<p>Cons: it is not very accurate in a few different ways, including having a large sensitivity to finite-time-step effects and also can result in MPS with rather large bond dimensions, more than what more accurate methods can provide</p>
<p>More information including a paper reference here: <br>
<a rel="nofollow" href="http://itensor.org/docs.cgi?vers=cppv3&page=formulas/tevol_mps_mpo">http://itensor.org/docs.cgi?vers=cppv3&page=formulas/tevol_mps_mpo</a></p></li>
<li><p>using the Trotter method but with additional "swaps" or "swap gates":</p>
<p>Pros: this method is the most reliable, in terms of being sure of convergence once it is implemented in a correct way. It is also not too hard to program. It can give very good accuracy too.</p>
<p>Cons: we don't have this available in a fully automatic way in the C++ version of ITensor (we do now in the Julia version, though). So you will have to implement the "swap" moves yourself, which temporarily bring further-neighbor sites together to become nearest neighbor.</p></li>
<li><p>using the TDVP method</p>
<p>Pros: this method is the best one to use, if you want the most state-of-the-art accuracy and efficiency. It has a very small time-step error and gives very accurate results, with relatively low bond dimensions. You can take rather large time steps for efficiency while still getting good results.</p>
<p>Cons: it is the most technical of the three to program. Also <em>caution</em> it can fail to converge if the initial state of the MPS has a poor basis, such as a product state or a state which has small overlap with the ideal state at a slightly later time. One way to overcome this initial-state problem is to start by using one of the other techniques above (Trotter is recommended for this) for a short time, then switch to TDVP. Or switch from one-site to two-site TDVP. Finally, one can use newer, more sophisticated TDVP convergence techniques such as in this recent paper: <a rel="nofollow" href="https://arxiv.org/abs/2005.06104">https://arxiv.org/abs/2005.06104</a></p>
<p>The TDVP method has been implemented in ITensor as an external code, and is available here:<br>
<a rel="nofollow" href="https://github.com/ITensor/TDVP">https://github.com/ITensor/TDVP</a></p></li>
</ol>
<p>Best regards,<br>
Miles</p>
http://itensor.org/support/2558/itensor-calculate-heisenberg-model-correlation-function?show=2559#a2559Fri, 25 Sep 2020 19:37:43 +0000Answered: Error loading MPS from file
http://itensor.org/support/2555/error-loading-mps-from-file?show=2556#a2556
<p>Hi, thanks for the question. The way the write-to-disk system works in the C++ version, currently, results in us being only able to guarantee that files are readable within the same version of the code and on the same machine (due to the use of a non-portable binary format). So it's not really intended for long-term or portable storage of results, so much as for techniques like write-to-disk within DMRG to prevent running out of RAM.</p>
<p>Because of these limitations, we're working on HDF5 support and it's pretty far along but not quite done yet. (Another reason for the HDF5 support is so files can be read and written between the C++ and Julia versions of ITensor.)</p>
<p>More specifically to your issue: were the files you were reading definitely written with a different version of the library? This would be especially relevant if the older version was version 2.x and the newer one version 3.x. I couldn't tell from your question if that was definitely the case, but it would be an important detail to know. My best guess at the moment is that this was the case, and that a change we made to the internal layout of a data type from one version to another made those older files not readable by the latest version.</p>
<p>Finally, yes the Electron site set and Hubbard site sets are identical in terms of their physical meaning and purpose, as well as which operators they offer and QN's they support etc. But one crucial (though small) difference is that the Index tags generated by the Electron site set include the tag "Electron". (Actually I think the change from Hubbard to Electron coincided with the introduction of Index tags so there weren't any tags per se associated to the Hubbard site set.)</p>
<p>Best regards,<br>
Miles</p>
http://itensor.org/support/2555/error-loading-mps-from-file?show=2556#a2556Thu, 24 Sep 2020 19:15:41 +0000Answered: error message in the code formula for DRMG computing excited states
http://itensor.org/support/2546/error-message-code-formula-for-drmg-computing-excited-states?show=2553#a2553
<p>(Question answered in discussion comments above.)</p>
http://itensor.org/support/2546/error-message-code-formula-for-drmg-computing-excited-states?show=2553#a2553Wed, 23 Sep 2020 17:50:29 +0000Answered: Contraction of Multiple ITensors?
http://itensor.org/support/2538/contraction-of-multiple-itensors?show=2543#a2543
<p>Hi Jin,<br>
Thanks for the question. So this is the intended, and expected behavior of the ITensor * operator, namely that first A and B are contracted, then the result of that is contracted with C.</p>
<p>One reason for this is that this is just how operators work in C++. There is no notation in C++ that would allow simultaneous contraction of three or more ITensors in that language using operator overloading (*,+, and similar), apart from defining a function call such as <code>multicontract(A,B,C,D,...)</code> (which we might do in the future).</p>
<p>Another reason is that this behavior is quite often the desired behavior that one does want, so it is not in any way a bad thing. It just may not have been what you were expecting. The ITensor interface is based on tensor diagram notation which also uses a pairwise contraction convention. Contracting over an index shared between three or more tensors requires the notion of a "hyperedge" in a tensor network graph, which is perfectly fine to introduce but I'm just mentioning it to say it's not the standard thing that diagrams express.</p>
<p>We do offer something like a hyperedge in ITensor though: it is the <code>delta(m,n,p)</code> ITensor, which is a special ITensor with all its (multi-)diagonal elements set to 1.0. Not all routines involving <code>delta</code> tensors are as optimized as they could be, though some are and in general it's a useful tool.</p>
<p>Hope that helps -</p>
<p>Miles</p>
http://itensor.org/support/2538/contraction-of-multiple-itensors?show=2543#a2543Tue, 22 Sep 2020 15:53:38 +0000Answered: Extended hubbard model ground state energy not converging for negative V
http://itensor.org/support/2432/extended-hubbard-ground-state-energy-converging-negative?show=2537#a2537
<p>Hi Streetama,</p>
<p>When I was computing E.H.M. ground states for V > U > 0, which nearly approaches a product state as V >>> U, the entanglement goes down.</p>
<p>This sounds to us as a good thing, but in fact with DMRG it is a bad thing because it takes an extremely large number of fast sweeps in order to converge. In essence, the small number of nonzero entries in the SVD leads to poor communication of information across the lattice with each sweep.</p>
<p>For instance, I believe I needed to run hundreds of sweeps to get the energy to settle down, even for small system sizes, and I observed the entanglement entropy changed very slowly with each sweep.</p>
<p>In order to test this, I'd recommend changing your sweeps parameters so that you stay at a single maxdim for several hundred sweeps and wait until the energy settles down before increasing maxdim.</p>
<p>On the other hand, if your boundary conditions are incorrect (for instance, anti-periodic instead of periodic) you can also see wild changes in sweep to sweep energy; I experienced this error one time due to a mistake in my definition of the Hamiltonian.</p>
<p>If you figure it out please post back here as I'm interested to know what you find, as I am continuing to use these methods.</p>
<p>Good luck!</p>
http://itensor.org/support/2432/extended-hubbard-ground-state-energy-converging-negative?show=2537#a2537Mon, 21 Sep 2020 14:18:02 +0000Answered: How ITensor simulate Kitaev honeycomb model?
http://itensor.org/support/2532/how-itensor-simulate-kitaev-honeycomb-model?show=2533#a2533
<p>Hi, thanks for the question. Are you interested in doing this for the C++ or Julia version? I’ll assume C++ and for Julia it’s actually quite similar.</p>
<p>We have an example code of doing a 2D system you can use here:<br>
<a rel="nofollow" href="http://itensor.org/docs.cgi?vers=cppv3&page=formulas/2d_dmrg">http://itensor.org/docs.cgi?vers=cppv3&page=formulas/2d_dmrg</a></p>
<p>The only difference from a 1D code in that example is that the AutoMPO part of the code runs over site numberings which are obtained from an array of “LatticeBond” objects that are returned from the <code>triangularLattice</code> function. You can see the code for this function here:<br>
<a rel="nofollow" href="https://github.com/ITensor/ITensor/blob/v3/itensor/mps/lattice/triangular.h">https://github.com/ITensor/ITensor/blob/v3/itensor/mps/lattice/triangular.h</a></p>
<p>Despite the apparent complexity of that function (<code>triangularLattice</code>) it is actually doing something really simple: it is making an array of pairs of integers, such as (n,n+1) and (n,n+Ny-1), etc. which define the sites on which the Hamiltonian terms should act, using a 1D ordering of the sites. This is because an MPS always has a 1D ordering of its sites, so to implement a 2D Hamiltonian you have to define some mapping of the 2D bonds (pairs of sites) to pairs of sites in the 1D, MPS ordering. The AutoMPO system takes care of the rest. Usually the 2D to 1D mapping used is just a “zig zag” pattern that goes up each column of the 2D system.</p>
<p>To implement the honeycomb lattice, then, all you have to do is come up with such a 2D to 1D mapping. I would recommend reshaping the honeycomb lattice first to a square lattice but with some bonds missing and perhaps some bonds added if necessary. Then on paper enumerate the sites from 1,2,...,N where N=Nx*Ny. Now make a function which generates the integer pairs of all the 2D Hamiltonian bonds following this enumeration and returns an array of structs (data structures) of these integer pairs.</p>
<p>A helpful practice step is to modify the 2D DMRG code linked above to just print out the values <code>bnd.s1</code> and <code>bnd.s2</code>. Compare these values to the numberings of sites of the triangular lattice following the zig zag convention I mentioned above.</p>
<p>Best regards,<br>
Miles</p>
http://itensor.org/support/2532/how-itensor-simulate-kitaev-honeycomb-model?show=2533#a2533Sun, 20 Sep 2020 18:09:03 +0000Answered: Details of How DMRG works
http://itensor.org/support/2529/details-of-how-dmrg-works?show=2530#a2530
<p>Hi Arnab,<br>
Thanks for the question. It seems like it has multiple parts. Let me briefly answer each below.</p>
<ol>
<li><p>DMRG is globally a type of variational algorithm, yes. So it can get stuck in a local minimum, and this can be prevented by choosing a good initial state (such as a very random initial state or one close to the ground state in some way), as well as by using the "DMRG noise term" which we provide as one of the DMRG parameters you can set through the Sweeps object. However, this does not mean that DMRG is much like gradient descent. For one thing, it is usually much faster to converge than gradient descent and is more reliable for obtaining high precision results.</p></li>
<li><p>As far as how DMRG works in the details, it would be hard to give a satisfactory answer here, and could be the topic of a semester-long course. I have written a pretty detailed article at the following link you could use though:<br>
<a rel="nofollow" href="http://tensornetwork.org/mps/algorithms/dmrg/">http://tensornetwork.org/mps/algorithms/dmrg/</a><br>
Also there are some articles you could find on DMRG. Finally, there are some slides for a series of talks I gave, linked from this page:<br>
<a rel="nofollow" href="http://tensornetwork.org/reviews_resources.html">http://tensornetwork.org/reviews_resources.html</a></p></li>
</ol>
<p>Lastly, how did you find the tutorial page you linked to? Was it through a Google search? I ask because that page is rather out of date and no longer linked from anywhere on the current ITensor website as far as I know, so I should probably remove those files. </p>
<p>Thanks,<br>
Miles</p>
http://itensor.org/support/2529/details-of-how-dmrg-works?show=2530#a2530Fri, 18 Sep 2020 16:41:58 +0000How to implement symmetry which anticommutes with hamiltonian
http://itensor.org/support/2510/how-implement-symmetry-which-anticommutes-with-hamiltonian
<p>Dear community,</p>
<p>How is it possible to implement the conservation of an anti-block structure for {H,U} = 0? </p>
<p>Let us consider for instance the example H = ∑ σˣᵢ + ∑ σˣᵢ σˣⱼ σˣₖ with U = ∏ σˣᵢ where the z-parity only anticommutes with the hamiltonian. Right now I am implementing this using the square of the Hamiltonian, since then [H²,U]=0 and we can use regular quantum numbers; however, this is a very bad solution. Can you think of a better way?</p>
<p>Best,</p>
<p>v.</p>
http://itensor.org/support/2510/how-implement-symmetry-which-anticommutes-with-hamiltonianFri, 11 Sep 2020 09:53:01 +0000Answered: How do we take into account QN conservation in self-writing an MPO?
http://itensor.org/support/2502/how-do-take-into-account-qn-conservation-self-writing-an-mpo?show=2503#a2503
<p>Hi Sergi,<br>
Thanks for the question. This is definitely a rather more complicated, technical topic that we have documentation for at the moment. </p>
<p>To begin with, please look at the question and answer here, which is similar to yours:<br>
<a rel="nofollow" href="http://itensor.org/support/2083/properly-handle-quantum-number-for-system-spin-half-moments">http://itensor.org/support/2083/properly-handle-quantum-number-for-system-spin-half-moments</a></p>
<p>If you understand everything in the discussion there, then you will be a long way toward understanding all of the aspects of the code in Heisenber.h. If not, then please ask some more questions in the comments below about the parts you do not yet understand.</p>
<p>To answer some of your questions above more specifically:</p>
<ul>
<li><p>the convention for the blocking of the tensors in the Heisenberg.h code (and in QN conserving ITensors more generally) is set by how the Index objects are constructed. The ordering and arrangement of QN blocks (QN subspaces) determines, ahead of time, the blocking pattern of the tensors</p></li>
<li><p>when various terms are added into the W tensors in that code, the addition operator of ITensor automatically figures out where the terms should go into the existing W tensor. So if the term being added in has certain non-zero blocks, then because the Index objects are the same (and carry all of the QN details), the ITensor system can figure out on its own how to correctly place the tensor being added into the block structure of the W tensor. So you don’t really have to manage this yourself; you just have to add ITensors together that carry the same total QN flux and it always works correctly (or you get an error if the flux is different).</p></li>
<li><p>for your Jordan-Wigner strings, it is a complication but you may find it’s not too bad of one. In a normal (non fermionic) MPO, there will be identity operators that go before a set of non-identity operators, or after. These will remain identity operators in your case. But there will be some identity operators which go in between a pair of fermionic operators (operators which change the fermion parity, such as C and Cdag). These should be replaced by F operators.</p></li>
<li><p>the 2D aspect is more of a serious complication, but I’m sure you know how to handle it, just mapping terms in 2D into various 1D distances. E.g. on a square lattice of “width” Ny, horizontal, nearest-neighbor terms (which have a 2D distance of 1) have a 1D distance of Ny (assuming you are using the “zig zag” MPS path which always goes up each column, rather than a snaking path which goes up odd columns and down even columns. I recommend the zig zag path.)</p></li>
</ul>
<p>Hope that helps you make some progress. One thing I like to do is to devise a bunch of tests of a new MPO I’m making by using the ITensor function <code>inner</code> to compute matrix elements between various product states. Like you can make a product state |phi<em>j> which has a single fermion on some site j and |phi</em>k> which has a single fermion on site k, then compute <phi<em>k|H|phi</em>j> and work out by hand what it should be for your H. Then you can check whether you get the right thing from inner. Often you can do this for every single term in the Hamiltonian and thus be nearly sure that it’s bug free. (I say nearly because checking the JW string requires at least two particles to be present, but you can do checks for that too.) Also of course you can do some DMRG calculations in limits where you know what the answer should be.</p>
<p>Best,<br>
Miles</p>
<p>P.S. as mentioned please ask more question in the comments below if you have them</p>
http://itensor.org/support/2502/how-do-take-into-account-qn-conservation-self-writing-an-mpo?show=2503#a2503Mon, 07 Sep 2020 16:48:41 +0000Answered: Implementing Jaynes–Cummings–Hubbard model using Julia
http://itensor.org/support/2491/implementing-jaynes-cummings-hubbard-model-using-julia?show=2498#a2498
<p>Hi, so yes you can definitely implement this model, but with one major limitation, which is that for any degree of freedom which is a boson (such as a photon mode), you'll have to limit the maximum number of states of the Hilbert space of that boson. This is just because ITensor and tensor network methods generally (barring some very specialized approaches) are formulated in tensor products of finite-dimensional vector spaces.</p>
<p>We have not yet defined a boson degree of freedom that gets included with ITensor, but we have made it straightforward to define custom site types or Hilbert spaces. For a detailed walkthrough of how to do this, you can see the following two example pages:<br>
<a rel="nofollow" href="http://itensor.org/docs.cgi?vers=julia&page=formulas/sitetype_basic">http://itensor.org/docs.cgi?vers=julia&page=formulas/sitetype_basic</a><br>
<a rel="nofollow" href="http://itensor.org/docs.cgi?vers=julia&page=formulas/sitetype_qns">http://itensor.org/docs.cgi?vers=julia&page=formulas/sitetype_qns</a></p>
<p>Once you define overloads of the <code>op</code> function which specify operator names associated to your custom site type or Hilbert space, you can use these within the AutoMPO feature of ITensor to include your custom operator names, similar to other examples of using AutoMPO where there are operator names like "Sz", "S+", "S-" for the case of spin Hilbert spaces.</p>
<p>I'd recommend testing everything out on the smallest possible system and comparing to (numerically) exact calculations to check that it's all working the way you expect.</p>
<p>If you do end up making a boson Hilbert space definition, please consider contributing it to our library by sending us a pull request on Github. We can work with you to make it ready to include into the library if you think it would be a good idea.</p>
<p>Best regards,<br>
Miles</p>
http://itensor.org/support/2491/implementing-jaynes-cummings-hubbard-model-using-julia?show=2498#a2498Sat, 05 Sep 2020 02:42:02 +0000Answered: Inconsistency between DMRG ground state energy and <psi|H|psi>
http://itensor.org/support/2477/inconsistency-between-dmrg-ground-state-energy-and-psi-psi?show=2480#a2480
<p>Hi,</p>
<p>Thanks for the question. It looks like a problem with how the AutoMPO is defined. It should work if you change the definition to:</p>
<pre><code> ampo += "Cdag",j+1,"C",j
ampo += "Cdag",j,"C",j+1
</code></pre>
<p>This is pretty tricky, and easy to mess up, but for the sake of getting the correct Fermion signs in your Hamiltonian the order of the operators matters. Please look over the nice tutorial on Fermions by Miles here: <a rel="nofollow" href="https://itensor.org/docs.cgi?page=tutorials/fermions">https://itensor.org/docs.cgi?page=tutorials/fermions</a> to understand this better.</p>
<p>Cheers,<br>
Matt</p>
http://itensor.org/support/2477/inconsistency-between-dmrg-ground-state-energy-and-psi-psi?show=2480#a2480Thu, 03 Sep 2020 22:04:54 +0000Answered: Selecting specific rows, columns, i.e. fancy indexing in ITensor
http://itensor.org/support/2430/selecting-specific-rows-columns-fancy-indexing-in-itensor?show=2472#a2472
<p>The answer Miles gave above in the comments is correct. Unfortunately right now this feature is a work in progress (something we think about periodically but haven't taken the time to implement). To explain some of the complications, the design is fairly straightforward for slicing dense ITensors, but for block sparse ITensors the slicing becomes a bit more subtle (i.e., do you only only allow slicing entire blocks, or also subblocks, of a block sparse ITensor). In addition, the design we were thinking of would involve the indices themselves also getting sliced (i.e. in your example, the <code>U_new</code> tensor would have indices <code>(u, v => 1:dim_cn)</code> where <code>v = commonind(V,Σ)</code>, instead of an entirely new index <code>c</code>). Sorry for the inconvenience, the strategy you take above seems fine for now. If you find that it is not fast enough for any reason, or need something more sophisticated that is not available right now, we may be able to help by pointing out certain functions or providing helper functions for certain operations.</p>
http://itensor.org/support/2430/selecting-specific-rows-columns-fancy-indexing-in-itensor?show=2472#a2472Wed, 02 Sep 2020 15:27:12 +0000Answered: About the excited state of electron wave packet using the toMPO
http://itensor.org/support/2459/about-the-excited-state-electron-wave-packet-using-the-tompo?show=2463#a2463
<p>Hi, I'm not sure I totally see what you are asking, but is your question about doing the following steps:<br>
1. compute the ground state<br>
2. act on the ground state with an operator that creates an electron wave packet?</p>
<p>I think I see from your sample code that this is what you are trying to do. </p>
<p>Unfortunately there you may be running into a long-standing limitation of the AutoMPO system, which is that it does not correctly create a sum of single, <em>fermionic</em> C or Cdag operators. This is due to the necessity of including Jordan-Wigner string on all sites to the left of the operator, which is correctly handled for a pair of such operators but not currently for a single operator. So unfortunately it is a bug in ITensor just for this one case.</p>
<p>As a workaround for now, I could help you to make a custom code that creates the MPO you want, of the form \sum<em>i a</em>i C<em>i where a</em>i is any set of coefficients and C_i is the electron annihilation operator. If you email me at mstoudenmire@flatironinstitute.org we can correspond about how to make this code. It is actually rather short code but you may need my help to make it correctly.</p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2459/about-the-excited-state-electron-wave-packet-using-the-tompo?show=2463#a2463Mon, 31 Aug 2020 15:30:08 +0000Create a symmetric copy of a MPS: How to transpose QN?
http://itensor.org/support/2460/create-a-symmetric-copy-of-a-mps-how-to-transpose-qn
<p>Hi folks, <br>
I am trying to copy the first 1...L÷2 matrices of an MPS to the last L÷2+1...L matrices (in order to get the symmetric copy of the MPS). the layout is as following:</p>
<pre><code>A - B - C - U λ - V - D - E - F
| | | | | | | |
=> A - B - C - U λ - U - C - B - A
| | | | | | | |
</code></pre>
<p>The problem I am having right now is that I am not able to link Uλ with U. However, since λ is diagonal, this should be possible in principle. In particular, this works without quantum numbers, but with quantum numbers somehow the order of the blocks is reversed. Do you have an idea how I could go on in that situation? Here some code:</p>
<pre><code>L = 8
maxdim = 20
sites = siteinds("S=1/2",L,conserve_szparity=true)
ψ = randomMPS(sites,[rand(Bool) ? "↑" : "↓" for i in 1:L]);
truncate!(ψ,maxdim=maxdim)
orthogonalize!(ψ,L÷2);
U, λ, V = svd(ψ[L÷2]*ψ[L÷2+1], uniqueinds(ψ[L÷2],ψ[L÷2+1]))
ψ_new = copy(ψ)
s_ind1 = siteindex(ψ,L)
s_ind2 = siteindex(ψ,1)
bondL = commonind(ψ[1],ψ[2])
ψ_new[L] = prime(replaceind(ψ[1],s_ind2,s_ind1),bondL)
for i in 2:L÷2-1
s_ind1 = siteindex(ψ,L-i+1)
s_ind2 = siteindex(ψ,i)
bondL = commonind(ψ[i],ψ[i+1])
bondR = commonind(ψ[i],ψ[i-1])
ψ_new[L-i+1] = replaceind(ψ[i],s_ind2,s_ind1)
prime!(ψ_new[L-i+1],bondL)
prime!(ψ_new[L-i+1],bondR)
end
ψ_new[L÷2] = U*λ
linku = commonind(U,λ)
linkv = commonind(V,λ)
bondL = commonind(ψ[L÷2],ψ[L÷2-1])
s_ind1 = siteindex(ψ,L÷2+1)
s_ind2 = siteindex(ψ,L÷2)
ψ_new[L÷2+1] = replaceind(U,s_ind2,s_ind1)
prime!(ψ_new[L÷2+1],bondL)
replaceind!(ψ_new[L÷2+1],linku,linkv)
</code></pre>
<p>The error I get in the last line here is</p>
<pre><code>Indices must have the same spaces to be replaced
</code></pre>
<p>If we look at linku and linkv, it becomes apparent that they do not coincide (in dimensionality and quantum numbers), even though λ is diagonal. This is something I do not quite understand, does this diagonality somehow change when using quantum numbers?</p>
<p>Best,</p>
<p>v.</p>
http://itensor.org/support/2460/create-a-symmetric-copy-of-a-mps-how-to-transpose-qnMon, 31 Aug 2020 10:11:05 +0000Answered: Hubbard model in magnetic field
http://itensor.org/support/2456/hubbard-model-in-magnetic-field?show=2457#a2457
<p>Hi Streetmanda,<br>
By default, the indices created in an Electron site set keep track of the Sz quantum number. So then an MPS made from these indices will be a state of well-defined Sz that will not be changed, since your Hamiltonian conserves total Sz. Throughout the calculation, the total Sz will remain at the value of the input state psi0 used to initialize the calculation. This is how DMRG calculations with conserved total quantum numbers are carried out in ITensor.</p>
<p>So if you'd like the magnetic field to be able to alter the magnetization, you'll need to turn off Sz conservation, like this:</p>
<pre><code>auto sites = Electron(N,{"ConserveSz=",false});
</code></pre>
<p>when making your site set <code>sites</code>.</p>
<p>For a list of the available options to the Electron site set you can see the documentation here:<br>
<a rel="nofollow" href="http://itensor.org/docs.cgi?vers=cppv3&page=classes/electron">http://itensor.org/docs.cgi?vers=cppv3&page=classes/electron</a></p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2456/hubbard-model-in-magnetic-field?show=2457#a2457Sun, 30 Aug 2020 14:45:31 +0000Answered: dmrg function not accepting MPO obtained by using nmultMPO
http://itensor.org/support/2453/dmrg-function-not-accepting-mpo-obtained-by-using-nmultmpo?show=2454#a2454
<p>Thanks for the question. So the issue here is that the site indices of the MPO HH do not have the prime levels expected for an MPO that is used as input to the dmrg function. If you print out HH, you'll see that each tensor has a site index with prime level 0 and a site index with prime level 2. That's in contrast to a usual MPO for a Hamiltonian in ITensor, where the prime levels of the site indices are 0 and 1. </p>
<p>The reason it's 0 and 2 in your case is that prime(H) raises the prime levels from 0 and 1 to 1 and 2, then contracting that MPO with H contracts over the prime-level-1 indices, leaving only the prime level 0 and 2 indices.</p>
<p>So a solution is just to add the line </p>
<pre><code>HH.mapPrime(2,1);
</code></pre>
<p>after you make HH, which will map any prime-level-2 indices to have prime level of 1 instead.</p>
<p>I'd encourage you to print out the MPO you are inputting into dmrg to make sure it has the structure and prime levels you want.</p>
<p>The more surprising thing here is that <code>inner(psi,HH,psi)</code> works. It might be a good idea in the future for us to make that more restrictive, but the current way that function works is that as long as one set of site indices of the MPO matches the MPS on the right, then the other site indices get automatically modified to match those of the MPS on the left. This is mentioned in the documentation here: <a rel="nofollow" href="http://itensor.org/docs.cgi?vers=cppv3&page=classes/mps_mpo_algs">http://itensor.org/docs.cgi?vers=cppv3&page=classes/mps_mpo_algs</a><br>
But I agree it can be a bit surprising in cases like this.</p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2453/dmrg-function-not-accepting-mpo-obtained-by-using-nmultmpo?show=2454#a2454Fri, 28 Aug 2020 15:40:44 +0000Answered: Commutators of MPO's
http://itensor.org/support/2446/commutators-of-mpos?show=2450#a2450
<p>Hi, so I'd recommend the following approach instead:</p>
<ol>
<li><p>expand the commutator into two terms (H on the left, H on the right) and compute these separately and/or use a symmetry to relate one to the other (on paper)</p></li>
<li><p>for each of these terms, say <Phi|H c^\dag<em>p c</em>q |Phi> compute an MPS "ccPhi" by acting c<em>q and c^\dag</em>p onto Phi. You can do this by acting those operators on the site index of the appropriate MPS tensor and re-setting the prime level back to zero for those indices. You'll also need to act with Jordan-Wigner string on the sites between p and q. (Same kind of operation, but just act with the operator named "F".)</p></li>
<li><p>compute the overlap <Phi|H|ccPhi> by using the inner(Phi,H,ccPhi) function</p></li>
</ol>
<p>That approach ought to be a lot faster than making an MPO for each c^\dag<em>p c</em>q pair. The only downside is needing to explicitly deal with Jordan-Wigner string though.</p>
<hr>
<p>On the other hand, if you do prefer to stick with the MPO based approach, and if it's fast enough for you (at a minimum it's a good check on the other approach) then I'd recommend not using nmultMPO to multiply MPOs together, but instead take advantage of the fact that you are ultimately taking an expectation value with MPS. So you will find it works better to do applyMPO to multiply each MPO onto |Phi> until only one MPO is left, then use the <code>inner</code> function to compute the matrix element of that leftover MPO.</p>
<p>So act the "Cdagup",i,"Cup",j MPO onto |Phi> using applyMPO, to get |ccPhi>, then compute <Phi|H|ccPhi>.</p>
<p>Hope that works well for you!</p>
<p>Miles</p>
http://itensor.org/support/2446/commutators-of-mpos?show=2450#a2450Thu, 27 Aug 2020 15:53:33 +0000Answered: Error regarding cmake samples
http://itensor.org/support/2439/error-regarding-cmake-samples?show=2448#a2448
<p>(Please see discussion above.)</p>
http://itensor.org/support/2439/error-regarding-cmake-samples?show=2448#a2448Thu, 27 Aug 2020 02:18:12 +0000Answered: removeqns(ITensor) in Julia
http://itensor.org/support/2440/removeqns-itensor-in-julia?show=2443#a2443
<p>Hi Junsen,<br>
This is a good question. For the Julia version of ITensor, we are soon planning to implement <code>removeqns</code> for the ITensor level but haven't just yet. </p>
<p>But if what you want for now is to map block sparse ITensors to dense ITensors, you can call the function <code>dense</code> on an ITensor and it will do the behavior that you are wanting.</p>
<p>The plan for <code>removeqns</code> is that it will keep other sparsity (such as diagonal sparsity) while removing QN information. This is in contrast to the <code>dense</code> functiono which removes all sparsity, whether associated with QNs or not.</p>
<p>So in short, please try <code>dense</code> on your ITensors. I'm implementing a version of that you can call directly on an MPS too right now, but with the current version you'll need to call it on each tensor yourself.</p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2440/removeqns-itensor-in-julia?show=2443#a2443Tue, 25 Aug 2020 17:23:57 +0000Answered: Forcing S=0 and total number of electrons in the Fermi-Hubbard model (Julia)
http://itensor.org/support/2431/forcing-total-number-electrons-the-fermi-hubbard-model-julia?show=2436#a2436
<p>No problem! This is a common question since the way the total quantum numbers (QNs), such as particle number, is fixed is kind of subtle in ITensor. It is fixed by your choice of initial state. So if you prepare the MPS you are using as an initial guess for DMRG (I assume you are planning to do a DMRG calculation) to be a state with a certain particle number, then that particle number will remain the same as long as you construct your MPS using site indices that carry QN information.</p>
<p>The line of code</p>
<pre><code>sites = siteinds("Electron",N)
</code></pre>
<p>is actually creating an array of N objects of type <code>Index</code>, so N electron sites, not N electrons.</p>
<p>To make these sites carry QN information, you need to change this line to:</p>
<pre><code>sites = siteinds("Electron",N,conserve_qns=true)
</code></pre>
<p>Then, to prepare an initial state with two electrons, say one being an up-spin electron and the other being a down-spin electron, you can use code such as:</p>
<pre><code>states = ["0" for n=1:N]
states[1] = "Up"
states[2] = "Dn"
psi = productMPS(sites,states)
</code></pre>
<p>You can also call <code>psi = randomMPS(sites,states,10)</code> to create a randomized MPS which has the site indices <code>sites</code>, the same total QN as given by the product state <code>states</code>, and a bond dimension of 10.</p>
<p>Then if you plug this <code>psi</code> MPS into DMRG as an initial state together with a Hamiltonian that conserves particle number, the way ITensor works is that the particle number is guaranteed not to change. This is because when you use Index objects that have QNs in them, only operations which change these QNs by a definite amount are allowed, and your Hamiltonian will change them by an amount which is zero if it conserves them.</p>
<pre><code>energy,psi = dmrg(H,psi,sweeps)
</code></pre>
<p>Please post a comment if you have any follow-up questions.</p>
<p>There is a full example of doing DMRG for the extended Hubbard model with QN conservation here:<br>
<a rel="nofollow" href="https://github.com/ITensor/ITensors.jl/blob/master/examples/dmrg/exthubbard.jl">https://github.com/ITensor/ITensors.jl/blob/master/examples/dmrg/exthubbard.jl</a></p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2431/forcing-total-number-electrons-the-fermi-hubbard-model-julia?show=2436#a2436Sun, 23 Aug 2020 22:57:59 +0000Answered: How to calculate Sz=1 sector magnetization?
http://itensor.org/support/2434/how-to-calculate-sz-1-sector-magnetization?show=2435#a2435
<p>Hi, thanks for the question. It's giving me some good ideas of how we can improve the documentation on the website.</p>
<p>To compute the ground state in the Sz=1 sector and measure its magnetization, you'll need to do the following three things:</p>
<ol>
<li><p>initialize your site set with the {"ConserveQNs=",true} option. (Note that you had a mistake in the code you put, with an extra "1" that shouldn't be there.) What this does is to make the Index objects in the 'sites' array carry QN information.</p></li>
<li><p>initialize your MPS to be a product state with a total Sz of 1. You can use the "InitState" feature of ITensor to do this. If you look at the sample code sample/dmrg.cc it shows a use of this feature, and you can change the rule of how "Up" and "Dn" are set to make the Sz be 1. (Note that this means the total QN is QN("Sz",2) actually, since we measure spin in units of 1/2.) You can call totalQN(psi) on an MPS psi to see what its total QN is.</p></li>
<li><p>after computing the ground state using DMRG, check that the totalQN is still QN("Sz",2). </p></li>
<li><p>measure the magnetization using code similar to on the front page of the itensor.org website. Here I copy that code below:</p></li>
</ol>
<p>for(int j = 1; j <= N; ++j)<br>
{<br>
//Make site j the MPS "orthogonality center"<br>
psi.position(j);<br>
//Measure magnetization<br>
Real Szj = elt(psi(j)<br>
* op(sites,"Sz",j)<br>
* dag(prime(psi(j),"Site")));<br>
println("Sz_",j," = ",Szj);<br>
}</p>
<p>Best,<br>
Miles</p>
http://itensor.org/support/2434/how-to-calculate-sz-1-sector-magnetization?show=2435#a2435Sun, 23 Aug 2020 18:05:30 +0000Answered: Jordan wigner fermi string in self-writing AutoMPO
http://itensor.org/support/2422/jordan-wigner-fermi-string-in-self-writing-autompo?show=2433#a2433
<p>Matt's answer is the right one, and do please see that article about fermions and how they are handled in ITensor.</p>
<p>To provide some additional information, there is currently only one place in ITensor where fermions are handled automatically for you, and that is in the AutoMPO system. So if you input Hamiltonian terms which contain fermionic operators (such as C and Cdag for spinless fermions, or Cup, Cdagup, Cdn, Cdagdn for electrons) then the AutoMPO system will use special rewriting rules and insert Jordan-Wigner string for you. (In the Julia version of ITensor, you can also extend this system for custom physical site types.) So the resulting MPO will be guaranteed to be correct in terms of treating fermionic operators.</p>
<p>On the other hand, when working with an MPS such as the one obtained after a DMRG calculation, you must insert Jordan-Wigner string operators yourself when measuring fermionic correlation functions, such as between a c-dagger and c operator acting on spatially separated sites. We have an example of how to do this for spinless fermions in the C++ version linked here:<br>
<a rel="nofollow" href="http://itensor.org/docs.cgi?vers=cppv3&page=formulas/spinless_correlator_mps">http://itensor.org/docs.cgi?vers=cppv3&page=formulas/spinless_correlator_mps</a></p>
<p>Hope that helps -</p>
<p>Miles</p>
http://itensor.org/support/2422/jordan-wigner-fermi-string-in-self-writing-autompo?show=2433#a2433Fri, 21 Aug 2020 15:47:41 +0000Answered: SVD swapping index arrow in TEBD algorithm with conserved quantum numbers
http://itensor.org/support/2421/swapping-index-arrow-algorithm-conserved-quantum-numbers?show=2429#a2429
<p>Hi Pietro,</p>
<p>I think using ITensor's MPS class is not necessary here, and makes it a bit confusing to keep track of the indices. Here is a minimal example of the step you are trying to reproduce from the paper, just in terms of ITensors:</p>
<pre><code>// Site indices
auto s = SpinHalf(2,{"ConserveQNs=",true});
auto sA = s(1);
auto sB = s(2);
// Link indices
auto lA = Index(QN(), 1, "lA");
auto lB = Index(QN(), 1, "lB");
// Gamma tensors
auto GammaA = randomITensor(QN(), dag(prime(lB)), sA, dag(lA));
auto GammaB = randomITensor(QN(), dag(prime(lA)), sB, dag(lB));
// Lambda tensors
auto lambdaA = randomITensor(QN(), lA, prime(lA));
auto lambdaB = randomITensor(QN(), lB, prime(lB));
// Fig. 3 (ii)
auto theta = lambdaB * GammaA * lambdaA * GammaB * lambdaB;
PrintData(inds(theta));
// Fig. 3 (iii)
auto [X, lambdaA_tilde, Y] = svd(theta, {lB, sA}, {"LeftTags = ", "lA_new", "RightTags = ", "lA_new_p"});
PrintData(inds(X));
PrintData(inds(lambdaA_tilde));
PrintData(inds(Y));
</code></pre>
<p>You can see there should be no Index mismatch, and if you are a bit careful with the indices you should be able to follow along with the next steps of the algorithm in the paper.</p>
<p>Cheers,<br>
Matt</p>
http://itensor.org/support/2421/swapping-index-arrow-algorithm-conserved-quantum-numbers?show=2429#a2429Sun, 09 Aug 2020 15:35:47 +0000Answered: A Question for the Input Tensor
http://itensor.org/support/2410/a-question-for-the-input-tensor?show=2427#a2427
<p>Hi Jiawen,</p>
<p>I'm working on a response to the email thread to send some examples of generating sparse ITensors.</p>
<p>It is not such an easy question to answer, since different physics problems and tensor network algorithms can lead to very different levels of sparsity, block sizes, tensor orders, etc. Often in ITensor we do not create large sparse tensors directly. Instead, they result organically from algorithms like DMRG, where blocks are generated on the fly in the SVD. Therefore, a good place to start would be to run common calculations like DMRG and extract tensors from the resulting MPS (like one in the middle of the system) for a variety of different problems. Note that specifying different symmetries of your problem (for example for the Hubbard model, choosing parity conservation vs. particle number conservation) is another way to generate tensors with different levels of sparsity.</p>
<p>Cheers,<br>
Matt</p>
http://itensor.org/support/2410/a-question-for-the-input-tensor?show=2427#a2427Fri, 07 Aug 2020 21:57:54 +0000Answered: Using IQTensor for general states
http://itensor.org/support/2395/using-iqtensor-for-general-states?show=2426#a2426
<p>(See the comments for an answer)</p>
http://itensor.org/support/2395/using-iqtensor-for-general-states?show=2426#a2426Fri, 07 Aug 2020 21:48:31 +0000Answered: Entanglement entropy (Julia)
http://itensor.org/support/2423/entanglement-entropy-julia?show=2424#a2424
<p>Hi Jacopo,</p>
<p>Here's a code for computing the von Neumann entropy in Julia:</p>
<pre><code>using ITensors
function entropy_von_neumann(psi::MPS, b::Int)
orthogonalize!(psi, b)
_,S = svd(psi[b], (linkind(psi, b-1), s[b]))
SvN = 0.0
for n in dim(S, 1)
p = S[n,n]^2
SvN -= p * log(p)
end
return SvN
end
N = 10
s = siteinds("S=1/2", N)
psi = randomMPS(s, 4)
SvN = entropy_von_neumann(psi, b)
</code></pre>
<p>Hopefully we will find time to create code formulas for common operations like this in Julia.</p>
<p>Cheers,<br>
Matt</p>
http://itensor.org/support/2423/entanglement-entropy-julia?show=2424#a2424Wed, 05 Aug 2020 20:01:11 +0000Answered: Purpose of various actions and parameters in replacebond! function?
http://itensor.org/support/2418/purpose-various-actions-parameters-replacebond-function?show=2419#a2419
<p>Hi Sujay,</p>
<p>1) The Spectrum object returns the eigenspectrum of the density matrix (the squared singular values). The idea is that, in the process of calculating the factors <code>L</code> and <code>R</code>, the eigenspectrum is often easily calculated as well, and it is a useful quantity for determining things like the entanglement entropy. It is returned so that you don't have to do extra work to calculate the eigenspectrum from either <code>L</code> or <code>R</code>, and users may want to print the eigenspectrum or return it from dmrg and perform calculation with it.</p>
<p>2) You may want to set normalize to true in cases like imaginary time evolution with TEBD, where if you don't normalize then the state's normalization will approach zero after some number of steps. <code>replacebond!</code> is a convenient place for that normalization to occur. By default it is chosen to be false, since it is application-dependent when someone may want that to occur, and users might want to normalize manually in case they want to save the norm (if it is physically relevant, for example).</p>
<p>3) The MPS/MPO types in ITensor can mostly be thought of as just vectors of ITensors that make up the MPS/MPO. However, they are a little more sophisticated than that, since they keep track of the orthogonality of the MPS/MPO. Information about the orthogonality is useful in various functions, where if you know the orthogonality than you can simplify certain expressions. So <code>l = leftlim(M)</code> is supposed to be set to <code>l</code>, such that sites <code>1:l</code> are guaranteed to be left orthogonal, and <code>r = rightlim(M)</code> is supposed to be set to <code>r</code>, such that sites <code>r:length(M)</code> are guaranteed to be right orthogonal.</p>
<p>This is helpful so that certain functions can assume that an MPS has a certain orthogonality so that they don't have to do extra work to reorthogonalize. For example, the <code>sample</code> function, which takes random samples of an MPS, assumes a certain orthogonality of the MPS that is input. In functions that manipulate tensors of an MPS/MPO, it is therefore good practice to keep track of the orthogonality so that extra work doesn't have to be done to unnecessarily reorthogonalize the MPS (or check for the orthogonality, which would be nearly as much work). Not keeping track of the orthogonality wouldn't lead to wrong code, but in general would require extra unnecessary work to be done.</p>
<p>-Matt</p>
http://itensor.org/support/2418/purpose-various-actions-parameters-replacebond-function?show=2419#a2419Wed, 29 Jul 2020 13:21:24 +0000Answered: How do you separate product of two ITensor objects if the two tensors do not have any common indices? (Julia)
http://itensor.org/support/2403/separate-product-itensor-objects-tensors-common-indices-julia?show=2416#a2416
<p>(Please see answer to question in discussion above.)</p>
http://itensor.org/support/2403/separate-product-itensor-objects-tensors-common-indices-julia?show=2416#a2416Tue, 28 Jul 2020 17:32:15 +0000Answered: Julia script for calculating energy gaps
http://itensor.org/support/2411/julia-script-for-calculating-energy-gaps?show=2412#a2412
<p>Hi Arnab,<br>
Thanks for the question - we do need to post a code example for this. Here is a short explanation though, and using it you ought to be able to adapt one of the other DMRG code examples to do excited states.</p>
<ol>
<li><p>say you calculate the ground state as follows:</p>
<p>energy0,psi0 = dmrg(H,psi0_i,sweeps)</p></li>
</ol>
<p>where here psi0_i is the initial guess for the ground state and psi0 is the optimized ground state.</p>
<ol>
<li><p>now you can calculate the first excited state as:</p>
<p>energy1,psi1 = dmrg(H,[psi0],psi1_i,sweeps;weight=weight)</p></li>
</ol>
<p>where psi1_i is the initial guess for the first excited state and <code>weight</code> is a positive number that you can adjust to penalize non-orthogonality of the ground and first excited state by different amounts (like a Lagrange multiplier).</p>
<ol>
<li><p>you can continue to calculate the second excited state as:</p>
<p>energy2,psi2 = dmrg(H,[psi0,psi1],psi2_i,sweeps; weight=weight)</p></li>
</ol>
<p>One tip is to do lots more sweeps for excited states than for ground states. Use your best judgement, and make sure that the energy is no longer changing over multiple sweeps before being sure things have converged. People often ask what value to take for the weight and I do not know because it is problem-dependent. Taking the weight to be 1.0 (the default) is good for most purposes though you can try other values to see if it speeds up convergence.</p>
<p>Hope that helps!</p>
<p>Miles</p>
http://itensor.org/support/2411/julia-script-for-calculating-energy-gaps?show=2412#a2412Tue, 28 Jul 2020 16:04:44 +0000Answered: Swapping indices of an MPS for Hubbard
http://itensor.org/support/2379/swapping-indices-of-an-mps-for-hubbard?show=2409#a2409
<p>See the comments for an answer.</p>
http://itensor.org/support/2379/swapping-indices-of-an-mps-for-hubbard?show=2409#a2409Tue, 28 Jul 2020 00:59:29 +0000