TBTK

To get an idea about the generality of problems that TBTK is intended to be able to handle, imagine a molecule on top of a graphene sheet, which in turn sits on top of a threedimensional magnetic substrate material. Further assume that we can model the three individual systems in the following way
To describe a system like this, we need three types of operators with three different types of index structure. We can for example introduce the operators \(a_{xo\sigma}\), \(b_{xys\sigma}\), and \(c_{xyzso}\) for the molecule, graphene, and substrate, respectively. Here \(x\), \(y\), and \(z\) corresponds to spatial coordinates, \(s\) is a sublattice index, \(o\) is an orbital index, and \(\sigma\) is a spin index. First we note that the number of indices per operator is not the same. Further, even though every operator have an \(x\)index, there is not necessarily any actual relationship between the different \(x\)indices. In particular, the molecule may be oriented along some axis which does not coincide with the natural coordinate axes of the other two materials, and even more importantly, there is no reason why \(x\) should run over the same number of values in the different materials. Rather, the \(x\)index is just a symbol indicating the first spatial index for the corresponding operator. Similarly, the sublattice and orbital indices for the different operators are not the same.
In TBTK systems like this can easily be modeled using flexible indices that compounds a set of indices into a list of nonnegative integers in curly braces. Such a compound index is usually referred to simply as an index, while the individual components are referred to as subindices. While we above used different letters to differentiate between operators with different index structures, in TBTK this is instead handled by introducing one more subsystem identifier at the front of the list of subindices. E.g. can can we write typical indices as (spin up = 0, spin down = 1)
Index  Description 

{0, 1, 0, 1}  Molecule (subsystem 0), site 1, orbital 0, spin down 
{1, 2, 3, 0, 0}  Graphene (subsystem 1), unit cell (2, 3), sublattice site 0, spin up 
{2, 3, 2, 1, 2, 3}  Substrate (subsystem 2), unit cell (3, 2, 1), sublattice site 2, orbital 3 
We have already mentioned one limitations on the indices, which is that they have to be nonnegative numbers. Although this is no real restriction on what types of problems that can be modeled, negative indices abounds in quantum mechanics and this is certainly not without inconvenience. However, the optimizations and additional features that are enabled by this design decision has been deemed far more important in this case. Nevertheless, support for negative indices could be added in the future through additional "syntactic sugar". Any developer interested in pursuing this direction is most welcome to discuss these ideas.
Another restriction has to do with the fact that the subsystem index was added at the front of the indices. This is not strictly required, at least in case the number of \(x\)indices are the same for all three operators. TBTK requires that systems only differ in their index structure to the right of a subindex for which they have different values. That is, by letting the first subsystem index be 0, 1, and 2 for the three different systems, the rest of the index structure for the three indices can be completely different.
To be more precise what it means for two systems to have different subindex structure: two systems differ in their subindex structure if some specific subindex runs over different number of values for the two systems, or if a particular subindex exist in one system but not in the other. This puts no real restriction on the types of problems that can be solved. However, more tricky situations than the one above can arise. Let us for example consider the case where the substrate above has different number of orbitals for the different sublatice sites. In this case it is an error to write the indices on the form {subsystem, x, y, z, orbital, sublattice}, because the orbitals run over different numbers of orbitals even though they can have identical values for all the subindices to the left of the orbital subindex. The original subindex order {subsystem, x, y, z, sublattice, orbital} given above does not have this problem though, since the sublattice index stands to the left of the orbital subindex and is different for the different sites. In general, ordering the subindices with "less local" subindices to the left should almost always resolve such issues.