Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adds task 1.13 to Superposition Kata #1382

Merged
merged 19 commits into from
Apr 22, 2024
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions katas/content/superposition/four_bitstrings/Placeholder.qs
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
namespace Kata {
operation FourBitstringSuperposition (qs : Qubit[], bits : Bool[][]) : Unit {
// Hint: remember that you can allocate extra qubits.

// Implement your solution here...
}
}
26 changes: 26 additions & 0 deletions katas/content/superposition/four_bitstrings/Solution.qs
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
namespace Kata {
operation FourBitstringSuperposition (qs : Qubit[], bits : Bool[][]) : Unit is Adj {
use anc = Qubit[2];
// Put two ancillas into equal superposition of 2-qubit basis states
ApplyToEachA(H, anc);

// Set up the right pattern on the main qubits with control on ancillas
for i in 0 .. 3 {
for j in 0 .. Length(qs) - 1 {
if bits[i][j] {
(ApplyControlledOnInt(i, X))(anc, qs[j]);
}
}
}

// Uncompute the ancillas, using patterns on main qubits as control
for i in 0 .. 3 {
if i % 2 == 1 {
(ApplyControlledOnBitString(bits[i], X))(qs, anc[0]);
}
if i / 2 == 1 {
(ApplyControlledOnBitString(bits[i], X))(qs, anc[1]);
}
}
}
}
104 changes: 104 additions & 0 deletions katas/content/superposition/four_bitstrings/Verification.qs
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
namespace Kata.Verification {
open Microsoft.Quantum.Convert;
open Microsoft.Quantum.Katas;
frtibble marked this conversation as resolved.
Show resolved Hide resolved

operation FourBitstringSuperposition_Reference (qs : Qubit[], bits : Bool[][]) : Unit is Adj {
use anc = Qubit[2];
ApplyToEachA(H, anc);

for i in 0 .. 3 {
for j in 0 .. Length(qs) - 1 {
if bits[i][j] {
(ApplyControlledOnInt(i, X))(anc, qs[j]);
}
}
}

for i in 0 .. 3 {
if i % 2 == 1 {
(ApplyControlledOnBitString(bits[i], X))(qs, anc[0]);
}
if i / 2 == 1 {
(ApplyControlledOnBitString(bits[i], X))(qs, anc[1]);
}
}
}

operation WState_Arbitrary_Reference (qs : Qubit[]) : Unit is Adj + Ctl {

let N = Length(qs);

if N ==1 {
// base case of recursion: |1⟩
X(qs[0]);
} else {
// |W_N⟩ = |0⟩|W_(N-1)⟩ + |1⟩|0...0⟩
// do a rotation on the first qubit to split it into |0⟩ and |1⟩ with proper weights
// |0⟩ -> sqrt((N-1)/N) |0⟩ + 1/sqrt(N) |1⟩
let theta = ArcSin(1.0 / Sqrt(IntAsDouble(N)));
Ry(2.0 * theta, qs[0]);

// do a zero-controlled W-state generation for qubits 1..N-1
X(qs[0]);
Controlled WState_Arbitrary_Reference(qs[0 .. 0], qs[1 .. N - 1]);
X(qs[0]);
}
}

@EntryPoint()
operation CheckSolution() : Bool {

// cross-tests
mutable bits = [[false, false], [false, true], [true, false], [true, true]];
frtibble marked this conversation as resolved.
Show resolved Hide resolved
tcNickolas marked this conversation as resolved.
Show resolved Hide resolved
if not CheckOperationsEquivalenceOnZeroStateWithFeedback(
FourBitstringSuperposition(_, bits),
ApplyToEachA(H, _),
2
) {
return false;
}

set bits = [[false, false, false, true], [false, false, true, false], [false, true, false, false], [true, false, false, false]];
if not CheckOperationsEquivalenceOnZeroStateWithFeedback(
frtibble marked this conversation as resolved.
Show resolved Hide resolved
FourBitstringSuperposition(_, bits),
WState_Arbitrary_Reference(_),
4
) {
return false;
}

// random tests
tcNickolas marked this conversation as resolved.
Show resolved Hide resolved
for N in 3 .. 10 {
// generate 4 distinct numbers corresponding to the bit strings
mutable numbers = [0, size = 4];

repeat {
mutable ok = true;
for i in 0 .. 3 {
set numbers w/= i <- DrawRandomInt(0, 1 <<< N - 1);
frtibble marked this conversation as resolved.
Show resolved Hide resolved
for j in 0 .. i - 1 {
if numbers[i] == numbers[j] {
set ok = false;
}
}
}
}
until (ok);

// convert numbers to bit strings
for i in 0 .. 3 {
set bits w/= i <- IntAsBoolArray(numbers[i], N);
}

if not CheckOperationsEquivalenceOnZeroStateWithFeedback(
FourBitstringSuperposition(_, bits),
frtibble marked this conversation as resolved.
Show resolved Hide resolved
FourBitstringSuperposition_Reference(_, bits),
N
) {
return false;
}
}

return true;
}
}
14 changes: 14 additions & 0 deletions katas/content/superposition/four_bitstrings/index.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
**Inputs:**

1. $N$ qubits in the $|0 \dots 0\rangle$ state.
2. Four bit string represented as `Bool[][]` `bits`.
tcNickolas marked this conversation as resolved.
Show resolved Hide resolved

`bits` is an array of size $4 * N$ which describes the bit strings as follows:
tcNickolas marked this conversation as resolved.
Show resolved Hide resolved
- `bits[i]` describes the *i*th bit string and has $N$ elements.
- All four bit strings will be distinct.

**Goal:** Create an equal superposition of the four basis states given by the bit strings.

**Example:**

For $N = 3$ and `bits = [[false, true, false], [true, false, false], [false, false, true], [true, true, false]]`, the state you need to prepare is $\frac{1}{2} \big(|010\rangle + |100\rangle + |001\rangle + |110\rangle\big)$.
26 changes: 26 additions & 0 deletions katas/content/superposition/four_bitstrings/solution.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
We are going to use the same trick of auxiliary qubits that we used in the previous task.

Since the desired superposition has 4 basis states with equal amplitudes, we are going to need two qubits to define a unique basis to control preparation of each of the basis states in the superposition.

We start by allocating two extra qubits and preparing an equal superposition of all 2-qubit states on them by applying an H gate to each of them:

$$\frac12 (|00\rangle + |01\rangle + |10\rangle + |11\rangle)_a \otimes |0 \dots 0\rangle_r$$

Then, for each of the four given bit strings, we walk through it and prepare the matching basis state on the main register of qubits, using controlled X gates with the corresponding basis state of the auxiliary qubits as control.

For example, when preparing the bit string `bits[0]`, we apply X gates controlled on the basis state $|00\rangle$; when preparing the bit string `bits[1]`, we apply X gates controlled on $|10\rangle$, and so on.

> We can choose an arbitrary matching of the 2-qubit basis states used as controls and the bit strings prepared on the main register.
> Since all amplitudes are the same, the result does not depend on which state controlled which bit string preparation.
> It can be convenient to use indices of the bit strings, converted to little-endian, to control preparation of the bit strings.
> Q# library function [`ApplyControlledOnInt`](https://learn.microsoft.com/en-us/qsharp/api/qsharp-lang/microsoft.quantum.canon/applycontrolledonint) does exactly that.

After this the system will be in the state

$$\frac12 (|00\rangle_a |bits_0\rangle_r + |10\rangle_a |bits_1\rangle_r + |01\rangle_a |bits_2\rangle_r + |11\rangle_a |bits_3\rangle_r)$$

As the last step, we must uncompute the auxiliary qubits, i.e., return them to the $|00\\rangle$ state to unentangle them from the main register.

Same as we did in the previous task, we will use [`ApplyControlledOnBitString`](https://learn.microsoft.com/en-us/qsharp/api/qsharp-lang/microsoft.quantum.canon/applycontrolledonbitstring) with the corresponding bit string and the X operation as arguments, the quantum register as the control, and the auxiliary qubits as the target.

We will uncompute each of them separately, so one of the auxiliary qubits will be uncomputed with the `bits[1]` and `bits[3]` bit strings as controls, and the other - with the `bits[2]` and `bits[3]`.
frtibble marked this conversation as resolved.
Show resolved Hide resolved
10 changes: 10 additions & 0 deletions katas/content/superposition/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,16 @@ This kata is designed to get you familiar with the concept of superposition and
]
})

@[exercise]({
"id": "superposition__four_bitstrings",
"title": "Four Bitstrings",
tcNickolas marked this conversation as resolved.
Show resolved Hide resolved
"path": "./four_bitstrings/",
"qsDependencies": [
"../KatasLibrary.qs",
"./Common.qs"
]
})

@[section]({
"id": "superposition__uneven_superpositions",
"title": "Uneven superpositions"
Expand Down
Loading