These code samples were written by Andres Paz and Mariia Mykhailova.
// Example 2-1: Random bit
operation RandomBit () : Unit {
// allocate one qubit
use q = Qubit();
// put it into superposition of 0 and 1
H(q);
// measure the qubit and store the result
let bit = M(q);
// make sure the qubit is back to the 0 state
Reset(q);
Message($"{bit}");
}
%simulate RandomBit
Zero
()
// Example 2-2: Random byte
// open namespace which defines arithmetic operations
open Microsoft.Quantum.Arithmetic;
operation RandomByte () : Unit {
// allocate 8 qubits
use qs = Qubit[8];
// put each qubit into superposition of 0 and 1
ApplyToEach(H, qs);
// measure the register and store the result
// MeasureInteger returns the qubits to the |0⟩ state, so no separate Reset is required
let randomByte = MeasureInteger(LittleEndian(qs));
Message($"{randomByte}");
}
%simulate RandomByte
224
()
// Example 2-3: Root-of-NOT
open Microsoft.Quantum.Diagnostics;
operation SqrtNOT (q : Qubit) : Unit is Adj+Ctl {
H(q);
S(q);
H(q);
}
operation RunSqrtNOT () : Unit {
// print matrix of the SqrtNOT operation
DumpOperation(1, ApplyToFirstQubitCA(SqrtNOT, _));
// allocate a qubit
use q = Qubit();
// apply SqrtNOT gate to the |0⟩ state
SqrtNOT(q);
Message("Qubit state after the first application of SqrtNOT");
DumpMachine();
// apply SqrtNOT gate again and verify that the qubit ends up in the |1⟩ state
SqrtNOT(q);
Message("Qubit state after the second application of SqrtNOT");
DumpMachine();
// make sure the qubit is back to the 0 state
Reset(q);
}
%simulate RunSqrtNOT
Qubit IDs | 1 |
---|---|
Unitary representation | $$ \left(\begin{matrix} 0.5 + 0.5i & 0.5 - 0.5i \\ 0.5 - 0.5i & 0.5 + 0.5i \end{matrix}\right) $$ |
Qubit state after the first application of SqrtNOT
Qubit IDs | 1 | ||
---|---|---|---|
Basis state (little endian) | Amplitude | Meas. Pr. | Phase |
$\left|0\right\rangle$ | $0.5000 + 0.5000 i$ | ↑ | |
$\left|1\right\rangle$ | $0.5000 -0.5000 i$ | ↑ |
Qubit state after the second application of SqrtNOT
Qubit IDs | 1 | ||
---|---|---|---|
Basis state (little endian) | Amplitude | Meas. Pr. | Phase |
$\left|0\right\rangle$ | $0.0000 -0.0000 i$ | ↑ | |
$\left|1\right\rangle$ | $1.0000 -0.0000 i$ | ↑ |
()
// Example 2-4: Quantum Spy Hunter
open Microsoft.Quantum.Diagnostics;
open Microsoft.Quantum.Measurement;
operation GetRangomBit () : Bool {
use q = Qubit();
H(q);
return MResetZ(q) == One;
}
// operation that performs the spy hunting protocol, including spy simulation if necessary
operation TryCatchASpy (spyPresent : Bool, spyAppliesH : Bool) : Bool {
use (a, fiber, b) = (Qubit(), Qubit(), Qubit());
// generate two random bits
let (sendApplyH, sendValue) = (GetRangomBit(), GetRangomBit());
// prepare Alice's qubit
if (sendValue) {
X(a);
}
if (sendApplyH) {
H(a);
}
// send the qubit!
SWAP(fiber, a);
// activate the spy
if (spyPresent) {
if (spyAppliesH) {
H(fiber);
}
let stolenData = M(fiber);
if (spyAppliesH) {
H(fiber);
}
}
// receive the qubit!
let receiveApplyH = GetRangomBit();
SWAP(fiber, b);
if (receiveApplyH) {
H(b);
}
let receiveValue = (M(b) == One);
// make sure all qubits are back to the 0 state
ResetAll([a, fiber, b]);
// Alice emails Bob to tell him her choice of operations and value.
// If the choice matches and the value does not, there's a spy!
return (sendApplyH == receiveApplyH) and (sendValue != receiveValue);
}
operation RunSpyHuntingProtocol () : Unit {
let spyPresent = true;
let spyAppliesH = false;
Message($"Settings: spy {spyPresent ? "" | "not "}present" +
(spyPresent ? $", spy {spyAppliesH ? "applies H" | "does not apply H"}" | ""));
let nAttempts = 1000;
mutable nCaught = 0;
for i in 1 .. nAttempts {
if (TryCatchASpy(spyPresent, spyAppliesH)) {
set nCaught += 1;
}
}
Message($"Caught the spy in {nCaught} out of {nAttempts} attempts");
}
%simulate RunSpyHuntingProtocol
Settings: spy present, spy does not apply H Caught the spy in 129 out of 1000 attempts
()