QSharp: PauliYGate

03 Jun 2015

C#, F#, Maths, QSharp, Quantum Computing


The quantum Y gate is represented by the Pauli-Y matrix. It can be used to perform Y operations on a single qubit.

In QSharp, the Y gate implementation is provided by the PauliYGate type. Like all QSharp gate implementations, this type inherits from the Matrix type, which describes a mathematical matrix structure used in all gate operations. The mathematics of the PauliYGate are discussed further in the Y command documentation.

Consider the following C# code, which demonstrates various PauliYGate type functionality:


public static void Main(string[] Arguments) 
{ 
    //  Construct a register with 2 random qubits
    Register oRegister = new Register(2); 

    //  Always check that we start off with a valid register
    if (oRegister.IsNormalised() == false) 
    { 
        oRegister.Normalise(); 
    } 

    //  Write the initial state to the console
    WriteQubits(oRegister); 
    WriteStateVector(oRegister); 
    Console.WriteLine(); 

    //  Construct a new Pauli Y gate
    PauliYGate oPauliYGate = new PauliYGate(); 

    //  What does the Pauli Y gate look like?
    Console.WriteLine("Pauli Y:"); 
    Console.WriteLine(oPauliYGate); 

    //  Apply the gate to qubit 0
    Console.WriteLine(); 
    Console.WriteLine("Y(0);"); 
    oRegister.StateVector = oPauliYGate.ApplyTo(oRegister); 

    //  Write the state to the console
    WriteStateVector(oRegister); 

    //  Apply the gate to qubit 0 - note that this is a reversible operation
    Console.WriteLine(); 
    Console.WriteLine("Y(0);"); 
    oRegister.StateVector = oPauliYGate.ApplyTo(oRegister); 

    //  Write the state to the console
    WriteStateVector(oRegister); 

    //  Now apply the gate to qubit 1 (this is also reversible operation)
    Console.WriteLine(); 
    Console.WriteLine("Y(1);"); 
    oRegister.StateVector = oPauliYGate.ApplyTo(1, oRegister); 

    WriteStateVector(oRegister); 
} 

private static void WriteQubits(Register Register) 
{ 
    Console.WriteLine(); 
    Console.WriteLine("Qubits:"); 

    for (int i = 0; i < Register.Qubits.Count; i++) 
    { 
        Console.Write("({0}|0> + {1}|1>)", Register.Qubits[i].AlphaLabel, Register.Qubits[i].BetaLabel); 

        if (i < (Register.Qubits.Count - 1)) 
        { 
            Console.Write(" (x) "); 
        } 
    } 

    Console.WriteLine(); 
} 

private static void WriteStateVector(Register Register) 
{ 
    Console.WriteLine(); 
    Console.WriteLine("State Vector:"); 
    Console.Write("|v> = ("); 

    for (int i = 0; i < Register.StateVector.Length; i++) 
    { 
        //  Using the overload to control the output
        Console.Write(Register.StateVector[i].ToString(true, false)); 

        if (i < (Register.StateVector.Length - 1)) 
        { 
            Console.Write(" + "); 
        } 
    } 

    Console.WriteLine(")"); 
} 

And again, this time in F#


type Program() = 

    [<EntryPoint>] 
    static let main argv =  

        //  Construct a register with 2 random qubits
        let oRegister = new Register(2) 

        //  Always check that we start off with a valid register
        if oRegister.IsNormalised() = false then 
            oRegister.Normalise() 

        //  Write the initial state to the console
        Program.WriteQubits(oRegister) 
        Program.WriteStateVector(oRegister) 
        printfn "" 

        //  Construct a new Pauli Y gate
        let oPauliYGate = new PauliYGate();  

        //  What does the Pauli Y gate look like?
        let sPauliY = oPauliYGate.ToString() 
        printfn "Pauli Y:" 
        printfn "%s" sPauliY 

        //  Apply the gate to qubit 0
        printfn "" 
        printfn "Y(0);"  
        oRegister.StateVector <- oPauliYGate.ApplyTo(oRegister);  

        //  Write the state to the console
        Program.WriteStateVector(oRegister);  

        //  Apply the gate to qubit 0 - note that this is a reversible operation
        printfn "" 
        printfn "Y(0);"  
        oRegister.StateVector <- oPauliYGate.ApplyTo(oRegister);  

        //  Write the state to the console
        Program.WriteStateVector(oRegister);  

        //  Now apply the gate to qubit 1 (this is also reversible operation)
        printfn "" 
        printfn "Y(1);"  
        oRegister.StateVector <- oPauliYGate.ApplyTo(1, oRegister);  

        Program.WriteStateVector(oRegister);  

        0 // return an integer exit code

    static member WriteQubits(register: Register) = 

        printfn "" 
        printfn "Qubits:" 

        for i in 0 .. (register.Qubits.Length - 1) do 
            let oQubit = register.Qubits.[i] 
            printf "(%s|0> + %s|1>)" oQubit.AlphaLabel oQubit.BetaLabel 

            if i < (register.Qubits.Length - 1) then 
                printf " (x) " 

        printfn "" 

    static member WriteStateVector(register: Register) =  

        printfn "" 
        printfn "State Vector:" 

        printf "|v> = (" 

        for i in 0 .. (register.StateVector.Length - 1) do 
            //  Using the overload to control the output
            let sState = register.StateVector.[i].ToString(true, true)  
            printf "%s" sState 

            if i < (register.StateVector.Length - 1) then 
                printf " + " 
             
        printfn ")" 

In QSharp, the PauliYGate can only really do one thing: be applied to a state vector.

This small program produces the following output:

State Vector:
|v> = (AC|00> + AD|01> + BC|10> + BD|11>)

Pauli Y:
{
{0,-i},
{i, 0}
}

Y(0);

State Vector:
|v> = (-iBC|00> + -iBD|01> + iAC|10> + iAD|11>)

Y(0);

State Vector:
|v> = (AC|00> + AD|01> + BC|10> + BD|11>)

Y(1);

State Vector:
|v> = (-iAD|00> + iAC|01> + -iBD|10> + iBC|11>)

* Note that coefficient values have not been written back to the console in this example


 

Copyright © 2024 carlbelle.com