Loading a Hamiltonian from file

The topic Obtaining energy level estimates demonstrates how to construct a Hamiltonian by adding individual terms to it. While this method is fine for small examples, quantum chemistry at scale require Hamiltonians with millions or billions of terms. Such Hamiltonians, generated by chemistry packages such as NWChem, are too large to import by hand. The sample presented here illustrates how a FermionHamiltonian instance may be automatically generated from a molecule represented by the Broombridge schema. For reference, one may inspect the provided LithiumHydrideGUI sample, or the RunSimulation sample. Limited support is also available for importing from the format consumed by LIQUi|>.

Now consider the example of the Nitrogen molecule, which is provided in the IntegralData/YAML/N2 folder of the samples repository. The method for loading the Broombridge schema is straightforward.

// The code snippets in this section require the following namespaces.
// Make sure to include these at the top of your file or namespace.
using Microsoft.Quantum.Chemistry;
using Microsoft.Quantum.Chemistry.Broombridge;
using Microsoft.Quantum.Chemistry.OrbitalIntegrals;
using Microsoft.Quantum.Chemistry.Fermion;
using Microsoft.Quantum.Chemistry.Paulis;
using Microsoft.Quantum.Chemistry.QSharpFormat;
using System.Linq;
    // This is the name of the file you want to load
    var filename = @"n2_1_00Re_sto3g.nw.out.yaml";
    // This is the directory containing the file
    var root = @"IntegralData\YAML\N2";
    // This creates a stream that can be passed to the deserializer
    using var textReader = System.IO.File.OpenText($@"{root}\{filename}");

    // This deserializes a Broombridge file, given its filename.
    var broombridge = BroombridgeSerializer.Deserialize(textReader);

    // Note that the deserializer returns a list of `ElectronicStructureProblem` instances,
    // as the file might describe multiple Hamiltonians. In this example, there is
    // only one Hamiltonian. So you use `.First()`, which selects the first element of the list.
    var problem = broombridge.First();

    // This extracts the `OrbitalIntegralHamiltonian` from Broombridge format,
    // then converts it to a fermion Hamiltonian, then to a Jordan-Wigner
    // representation.
    var orbitalIntegralHamiltonian = problem.OrbitalIntegralHamiltonian;
    var fermionHamiltonian = orbitalIntegralHamiltonian.ToFermionHamiltonian(IndexConvention.UpDown);
    var jordanWignerEncoding = fermionHamiltonian.ToPauliHamiltonian(QubitEncoding.JordanWigner);

The Broombridge schema also contains suggestions for the initial state to be prepared. The labels, for example, "|G⟩" or "|E1⟩", for these states may be seen by inspecting the file. In order to prepare these initial states, the qSharpData consumed by the Q# quantum algorithms is obtained similar to the previous section, but with an additional parameter selecting the desired initial state. For instance,

    // The desired initial state, assuming that a description of it's present in the
    // Broombridge schema.
    var state = "|E1>";
    var wavefunction = problem.InitialStates[state].ToIndexing(IndexConvention.UpDown);

    // This creates the qSharpData consumable by the Q# chemistry library algorithms.
    var qSharpHamiltonianData = jordanWignerEncoding.ToQSharpFormat();
    var qSharpWavefunctionData = wavefunction.ToQSharpFormat();
    var qSharpData = Convert.ToQSharpFormat(qSharpHamiltonianData, qSharpWavefunctionData);

You may also load a Hamiltonian from the LIQUi|> format, using a similar syntax.

    // This is the name of the file you want to load
    var filename = @"fe2s2_sto3g.dat"; // This is Ferredoxin.
    // This is the directory containing the file
    var root = @"IntegralData\Liquid";
    // This creates a stream that can be passed to the deserializer
    using var textReader = System.IO.File.OpenText($@"{root}\{filename}");

    // Deserialize the LiQuiD format.
    var problem = LiQuiDSerializer.Deserialize(textReader).First();

    // This extracts the `OrbitalIntegralHamiltonian` from Broombridge format,
    // then converts it to a fermion Hamiltonian, then to a Jordan-Wigner
    // representation.
    var orbitalIntegralHamiltonian = problem.OrbitalIntegralHamiltonian;
    var fermionHamiltonian = orbitalIntegralHamiltonian.ToFermionHamiltonian(IndexConvention.UpDown);
    var jordanWignerEncoding = fermionHamiltonian.ToPauliHamiltonian(QubitEncoding.JordanWigner);

    // This is a data structure representing the Jordan-Wigner encoding 
    // of the Hamiltonian that you may pass to a Q# algorithm.
    var qSharpHamiltonianData = jordanWignerEncoding.ToQSharpFormat();

By following this process from any instance of Broombridge, or any intermediate step, quantum algorithms such as quantum phase estimation may be run on the specified electronic structure problem.