Hi,

It seems the contraction * only works for two ITensors. If I have more than two ITensors that share one index, e.g. A(i,j)*B(i,k)*C(i,l) gives wrong results. Is there a function in this library doing this? Thanks.

Jin

+1 vote

Hi,

It seems the contraction * only works for two ITensors. If I have more than two ITensors that share one index, e.g. A(i,j)*B(i,k)*C(i,l) gives wrong results. Is there a function in this library doing this? Thanks.

Jin

Hi, could you please expand your question a bit more? What is the result that you expected and what is the result you are getting? We'd like to know if there is a bug or whether it's just surprising behavior.

Thanks,

Miles

Thanks,

Miles

Hi Miles,

I expect to sum over "i" and get a new tensor @@D(j,k,l) = \sum\_i A(i,j)B(i,k)C(i,l).@@

But A*B*C gives a four rank tensor. It contracts A and B first and then C.

I expect to sum over "i" and get a new tensor @@D(j,k,l) = \sum\_i A(i,j)B(i,k)C(i,l).@@

But A*B*C gives a four rank tensor. It contracts A and B first and then C.

0 votes

Best answer

Hi Jin,

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.

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 `multicontract(A,B,C,D,...)`

(which we might do in the future).

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.

We do offer something like a hyperedge in ITensor though: it is the `delta(m,n,p)`

ITensor, which is a special ITensor with all its (multi-)diagonal elements set to 1.0. Not all routines involving `delta`

tensors are as optimized as they could be, though some are and in general it's a useful tool.

Hope that helps -

Miles

...