This article may rely excessively on sources too closely associated with the subject, potentially preventing the article from being verifiable and neutral. Please help improve it by replacing them with more appropriate citations to reliable, independent, third-party sources. (September 2018) (Learn how and when to remove this message)
Q#
ParadigmQuantum, functional, imperative
Designed byMicrosoft Research (quantum architectures and computation group; QuArC)
DeveloperMicrosoft
First appearedDecember 11, 2017 (2017-12-11)
Typing disciplineStatic, strong
PlatformCommon Language Infrastructure
LicenseMIT License[1]
Filename extensions.qs
Websitedocs.microsoft.com/en-us/quantum
Influenced by
C#, F#, Python

Q# (pronounced as Q sharp) is a domain-specific programming language used for expressing quantum algorithms.[2] It was initially released to the public by Microsoft as part of the Quantum Development Kit.[3]

History

Historically, Microsoft Research had two teams interested in quantum computing: the QuArC team based in Redmond[which?],[4] directed by Krysta Svore, that explored the construction of quantum circuitry, and Station Q initially located in Santa Barbara and directed by Michael Freedman, that explored topological quantum computing.[5][6]

During a Microsoft Ignite Keynote on September 26, 2017, Microsoft announced that they were going to release a new programming language geared specifically towards quantum computers.[7] On December 11, 2017, Microsoft released Q# as a part of the Quantum Development Kit.[3]

At Build 2019, Microsoft announced that it would be open-sourcing the Quantum Development Kit, including its Q# compilers and simulators.[8]

Bettina Heim currently leads the Q# language development effort.[9][10]

Usage

Q# is available as a separately downloaded extension for Visual Studio,[11] but it can also be run as an independent tool from the command line or Visual Studio Code. The Quantum Development Kit ships with a quantum simulator which is capable of running Q#.[12]

In order to invoke the quantum simulator, another .NET programming language, usually C#, is used, which provides the (classical) input data for the simulator and reads the (classical) output data from the simulator.[13]

Features

A primary feature of Q# is the ability to create and use qubits for algorithms. As a consequence, some of the most prominent features of Q# are the ability to entangle and introduce superpositioning to qubits via Controlled NOT gates and Hadamard gates, respectively, as well as Toffoli Gates, Pauli X, Y, Z Gate, and many more which are used for a variety of operations; see the list at the article on quantum logic gates.[14]

The hardware stack that will eventually come together with Q# is expected to implement Qubits as topological qubits. The quantum simulator that is shipped with the Quantum Development Kit today is capable of processing up to 32 qubits on a user machine and up to 40 qubits on Azure.[15]

Documentation and resources

Currently, the resources available for Q# are scarce, but the official documentation is published: Microsoft Developer Network: Q#. Microsoft Quantum Github repository is also a large collection of sample programs implementing a variety of Quantum algorithms and their tests.

Microsoft has also hosted a Quantum Coding contest on Codeforces, called Microsoft Q# Coding Contest - Codeforces, and also provided related material to help answer the questions in the blog posts, plus the detailed solutions in the tutorials.

Microsoft hosts a set of learning exercises to help learn Q# on GitHub: microsoft/QuantumKatas with links to resources, and answers to the problems.

Syntax

Q# is syntactically related to both C# and F# yet also has some significant differences.

Similarities with C#

Similarities with F#

Differences

Example

The following source code is a multiplexer from the official Microsoft Q# library repository.

// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

namespace Microsoft.Quantum.Canon {
    open Microsoft.Quantum.Intrinsic;
    open Microsoft.Quantum.Arithmetic;
    open Microsoft.Quantum.Arrays;
    open Microsoft.Quantum.Diagnostics;
    open Microsoft.Quantum.Math;

    /// # Summary
    /// Applies a multiply-controlled unitary operation $U$ that applies a
    /// unitary $V_j$ when controlled by n-qubit number state $\ket{j}$.
    ///
    /// $U = \sum^{N-1}_{j=0}\ket{j}\bra{j}\otimes V_j$.
    ///
    /// # Input
    /// ## unitaryGenerator
    /// A tuple where the first element `Int` is the number of unitaries $N$,
    /// and the second element `(Int -> ('T => () is Adj + Ctl))`
    /// is a function that takes an integer $j$ in $[0,N-1]$ and outputs the unitary
    /// operation $V_j$.
    ///
    /// ## index
    /// $n$-qubit control register that encodes number states $\ket{j}$ in
    /// little-endian format.
    ///
    /// ## target
    /// Generic qubit register that $V_j$ acts on.
    ///
    /// # Remarks
    /// `coefficients` will be padded with identity elements if
    /// fewer than $2^n$ are specified. This implementation uses
    /// $n-1$ auxiliary qubits.
    ///
    /// # References
    /// - [ *Andrew M. Childs, Dmitri Maslov, Yunseong Nam, Neil J. Ross, Yuan Su*,
    ///      arXiv:1711.10980](https://arxiv.org/abs/1711.10980)
    operation MultiplexOperationsFromGenerator<'T>(unitaryGenerator : (Int, (Int -> ('T => Unit is Adj + Ctl))), index: LittleEndian, target: 'T) : Unit is Ctl + Adj {
        let (nUnitaries, unitaryFunction) = unitaryGenerator;
        let unitaryGeneratorWithOffset = (nUnitaries, 0, unitaryFunction);
        if Length(index!) == 0 {
            fail "MultiplexOperations failed. Number of index qubits must be greater than 0.";
        }
        if nUnitaries > 0 {
            let auxiliary = [];
            Adjoint MultiplexOperationsFromGeneratorImpl(unitaryGeneratorWithOffset, auxiliary, index, target);
        }
    }

    /// # Summary
    /// Implementation step of `MultiplexOperationsFromGenerator`.
    /// # See Also
    /// - Microsoft.Quantum.Canon.MultiplexOperationsFromGenerator
    internal operation MultiplexOperationsFromGeneratorImpl<'T>(unitaryGenerator : (Int, Int, (Int -> ('T => Unit is Adj + Ctl))), auxiliary: Qubit[], index: LittleEndian, target: 'T)
    : Unit {
        body (...) {
            let nIndex = Length(index!);
            let nStates = 2^nIndex;

            let (nUnitaries, unitaryOffset, unitaryFunction) = unitaryGenerator;

            let nUnitariesLeft = MinI(nUnitaries, nStates / 2);
            let nUnitariesRight = MinI(nUnitaries, nStates);

            let leftUnitaries = (nUnitariesLeft, unitaryOffset, unitaryFunction);
            let rightUnitaries = (nUnitariesRight - nUnitariesLeft, unitaryOffset + nUnitariesLeft, unitaryFunction);

            let newControls = LittleEndian(Most(index!));

            if nUnitaries > 0 {
                if Length(auxiliary) == 1 and nIndex == 0 {
                    // Termination case

                    (Controlled Adjoint (unitaryFunction(unitaryOffset)))(auxiliary, target);
                } elif Length(auxiliary) == 0 and nIndex >= 1 {
                    // Start case
                    let newauxiliary = Tail(index!);
                    if nUnitariesRight > 0 {
                        MultiplexOperationsFromGeneratorImpl(rightUnitaries, [newauxiliary], newControls, target);
                    }
                    within {
                        X(newauxiliary);
                    } apply {
                        MultiplexOperationsFromGeneratorImpl(leftUnitaries, [newauxiliary], newControls, target);
                    }
                } else {
                    // Recursion that reduces nIndex by 1 and sets Length(auxiliary) to 1.
                    let controls = [Tail(index!)] + auxiliary;
                    use newauxiliary = Qubit();
                    use andauxiliary = Qubit[MaxI(0, Length(controls) - 2)];
                    within {
                        ApplyAndChain(andauxiliary, controls, newauxiliary);
                    } apply {
                        if nUnitariesRight > 0 {
                            MultiplexOperationsFromGeneratorImpl(rightUnitaries, [newauxiliary], newControls, target);
                        }
                        within {
                            (Controlled X)(auxiliary, newauxiliary);
                        } apply {
                            MultiplexOperationsFromGeneratorImpl(leftUnitaries, [newauxiliary], newControls, target);
                        }
                    }
                }
            }
        }
        adjoint auto;
        controlled (controlRegister, ...) {
            MultiplexOperationsFromGeneratorImpl(unitaryGenerator, auxiliary + controlRegister, index, target);
        }
        adjoint controlled auto;
    }

    /// # Summary
    /// Applies multiply-controlled unitary operation $U$ that applies a
    /// unitary $V_j$ when controlled by n-qubit number state $\ket{j}$.
    ///
    /// $U = \sum^{N-1}_{j=0}\ket{j}\bra{j}\otimes V_j$.
    ///
    /// # Input
    /// ## unitaryGenerator
    /// A tuple where the first element `Int` is the number of unitaries $N$,
    /// and the second element `(Int -> ('T => () is Adj + Ctl))`
    /// is a function that takes an integer $j$ in $[0,N-1]$ and outputs the unitary
    /// operation $V_j$.
    ///
    /// ## index
    /// $n$-qubit control register that encodes number states $\ket{j}$ in
    /// little-endian format.
    ///
    /// ## target
    /// Generic qubit register that $V_j$ acts on.
    ///
    /// # Remarks
    /// `coefficients` will be padded with identity elements if
    /// fewer than $2^n$ are specified. This version is implemented
    /// directly by looping through n-controlled unitary operators.
    operation MultiplexOperationsBruteForceFromGenerator<'T>(unitaryGenerator : (Int, (Int -> ('T => Unit is Adj + Ctl))), index: LittleEndian, target: 'T)
    : Unit is Adj + Ctl {
        let nIndex = Length(index!);
        let nStates = 2^nIndex;
        let (nUnitaries, unitaryFunction) = unitaryGenerator;
        for idxOp in 0..MinI(nStates,nUnitaries) - 1 {
            (ControlledOnInt(idxOp, unitaryFunction(idxOp)))(index!, target);
        }
    }

    /// # Summary
    /// Returns a multiply-controlled unitary operation $U$ that applies a
    /// unitary $V_j$ when controlled by n-qubit number state $\ket{j}$.
    ///
    /// $U = \sum^{2^n-1}_{j=0}\ket{j}\bra{j}\otimes V_j$.
    ///
    /// # Input
    /// ## unitaryGenerator
    /// A tuple where the first element `Int` is the number of unitaries $N$,
    /// and the second element `(Int -> ('T => () is Adj + Ctl))`
    /// is a function that takes an integer $j$ in $[0,N-1]$ and outputs the unitary
    /// operation $V_j$.
    ///
    /// # Output
    /// A multiply-controlled unitary operation $U$ that applies unitaries
    /// described by `unitaryGenerator`.
    ///
    /// # See Also
    /// - Microsoft.Quantum.Canon.MultiplexOperationsFromGenerator
    function MultiplexerFromGenerator(unitaryGenerator : (Int, (Int -> (Qubit[] => Unit is Adj + Ctl)))) : ((LittleEndian, Qubit[]) => Unit is Adj + Ctl) {
        return MultiplexOperationsFromGenerator(unitaryGenerator, _, _);
    }

    /// # Summary
    /// Returns a multiply-controlled unitary operation $U$ that applies a
    /// unitary $V_j$ when controlled by n-qubit number state $\ket{j}$.
    ///
    /// $U = \sum^{2^n-1}_{j=0}\ket{j}\bra{j}\otimes V_j$.
    ///
    /// # Input
    /// ## unitaryGenerator
    /// A tuple where the first element `Int` is the number of unitaries $N$,
    /// and the second element `(Int -> ('T => () is Adj + Ctl))`
    /// is a function that takes an integer $j$ in $[0,N-1]$ and outputs the unitary
    /// operation $V_j$.
    ///
    /// # Output
    /// A multiply-controlled unitary operation $U$ that applies unitaries
    /// described by `unitaryGenerator`.
    ///
    /// # See Also
    /// - Microsoft.Quantum.Canon.MultiplexOperationsBruteForceFromGenerator
    function MultiplexerBruteForceFromGenerator(unitaryGenerator : (Int, (Int -> (Qubit[] => Unit is Adj + Ctl)))) : ((LittleEndian, Qubit[]) => Unit is Adj + Ctl) {
        return MultiplexOperationsBruteForceFromGenerator(unitaryGenerator, _, _);
    }

    /// # Summary
    /// Computes a chain of AND gates
    ///
    /// # Description
    /// The auxiliary qubits to compute temporary results must be specified explicitly.
    /// The length of that register is `Length(ctrlRegister) - 2`, if there are at least
    /// two controls, otherwise the length is 0.
    internal operation ApplyAndChain(auxRegister : Qubit[], ctrlRegister : Qubit[], target : Qubit)
    : Unit is Adj {
        if Length(ctrlRegister) == 0 {
            X(target);
        } elif Length(ctrlRegister) == 1 {
            CNOT(Head(ctrlRegister), target);
        } else {
            EqualityFactI(Length(auxRegister), Length(ctrlRegister));
            let controls1 = ctrlRegister[0..0] + auxRegister;
            let controls2 = Rest(ctrlRegister);
            let targets = auxRegister + [target];
            ApplyToEachA(ApplyAnd, Zipped3(controls1, controls2, targets));
        }
    }
}


References

  1. ^ "Introduction to Q#" (PDF). University of Washington.
  2. ^ a b QuantumWriter. "The Q# Programming Language". docs.microsoft.com. Retrieved 2017-12-11.
  3. ^ a b "Announcing the Microsoft Quantum Development Kit". Retrieved 2017-12-11.
  4. ^ "Solving the quantum many-body problem with artificial neural networks". Microsoft Azure Quantum. 15 February 2017.
  5. ^ Scott Aaronson's blog, 2013, 'Microsoft: From QDOS to QMA in less than 35 years', https://scottaaronson.blog/?p=1471
  6. ^ "What are the Q# programming language & QDK? - Azure Quantum". learn.microsoft.com. 12 January 2024.
  7. ^ "Microsoft announces quantum computing programming language". Retrieved 2017-12-14.
  8. ^ Microsoft is open-sourcing its Quantum Development Kit
  9. ^ "The Women of QuArC". 30 March 2019.
  10. ^ "Intro to Q# - Intro to Quantum Software Development". stem.mitre.org.
  11. ^ QuantumWriter. "Setting up the Q# development environment". docs.microsoft.com. Retrieved 2017-12-14.
  12. ^ Akdogan, Erman (23 October 2022). "Quantum computing is coming for finance & crypto". Medium.
  13. ^ "This Week in Programming: Get Quantum with Q Sharp". The New Stack. 16 December 2017.
  14. ^ "Qubit Gate - an overview". www.sciencedirect.com.
  15. ^ "Microsoft previews quantum computing development kit". CIO.
  16. ^ "Types in Q# - Microsoft Quantum". docs.microsoft.com. 27 July 2022.