qqz.grover

 1from typing import Optional
 2
 3import matplotlib.pyplot as plt
 4from qiskit import QuantumCircuit, Aer, transpile
 5from qiskit.visualization import plot_histogram
 6from qiskit.circuit import Gate
 7
 8
 9def grover(N_len: int, oracle_gate: Gate, oracle_qubits_len: int, k_time: int, show_hist: Optional[bool] = True) -> int:
10    qc = QuantumCircuit(N_len + oracle_qubits_len, N_len)
11
12    qc.h(range(N_len))
13
14    for _ in range(k_time):
15        qc.append(oracle_gate, range(N_len + oracle_qubits_len))
16
17        qc.h(range(N_len))
18        qc.x(range(N_len))
19
20        # MCZ
21        qc.h(N_len - 1)
22        qc.mct(list(range(N_len - 1)), N_len - 1)
23        qc.h(N_len - 1)
24
25        qc.x(range(N_len))
26        qc.h(range(N_len))
27
28    qc.measure(range(N_len), range(N_len))
29
30    backend = Aer.get_backend('aer_simulator_matrix_product_state')
31    qc = transpile(qc, backend)
32    job = backend.run(qc, shots=10000)
33    hist = job.result().get_counts()
34
35    if show_hist:
36        plot_histogram(hist)
37        plt.show()
38
39    return int(max(hist.items(), key=lambda x: x[1])[0], 2)
40
41
42def sample_oracle(N_len: int) -> Gate:
43    """
44    An oracle which inverts the sign if the number of 11 is odd.
45    11 が奇数個あるなら符号を反転するオラクル
46    """
47
48    qc = QuantumCircuit(N_len + 1)
49
50    for qubit in range(N_len - 1):
51        qc.ccx(qubit, qubit + 1, N_len)
52
53    qc.z(N_len)
54
55    for qubit in reversed(range(N_len - 1)):
56        qc.ccx(qubit, qubit + 1, N_len)
57
58    return qc.to_gate()
59
60
61if __name__ == '__main__':
62    print(grover(3, sample_oracle(3), 1, 1))
def grover( N_len: int, oracle_gate: qiskit.circuit.gate.Gate, oracle_qubits_len: int, k_time: int, show_hist: Union[bool, NoneType] = True) -> int:
10def grover(N_len: int, oracle_gate: Gate, oracle_qubits_len: int, k_time: int, show_hist: Optional[bool] = True) -> int:
11    qc = QuantumCircuit(N_len + oracle_qubits_len, N_len)
12
13    qc.h(range(N_len))
14
15    for _ in range(k_time):
16        qc.append(oracle_gate, range(N_len + oracle_qubits_len))
17
18        qc.h(range(N_len))
19        qc.x(range(N_len))
20
21        # MCZ
22        qc.h(N_len - 1)
23        qc.mct(list(range(N_len - 1)), N_len - 1)
24        qc.h(N_len - 1)
25
26        qc.x(range(N_len))
27        qc.h(range(N_len))
28
29    qc.measure(range(N_len), range(N_len))
30
31    backend = Aer.get_backend('aer_simulator_matrix_product_state')
32    qc = transpile(qc, backend)
33    job = backend.run(qc, shots=10000)
34    hist = job.result().get_counts()
35
36    if show_hist:
37        plot_histogram(hist)
38        plt.show()
39
40    return int(max(hist.items(), key=lambda x: x[1])[0], 2)
def sample_oracle(N_len: int) -> qiskit.circuit.gate.Gate:
43def sample_oracle(N_len: int) -> Gate:
44    """
45    An oracle which inverts the sign if the number of 11 is odd.
46    11 が奇数個あるなら符号を反転するオラクル
47    """
48
49    qc = QuantumCircuit(N_len + 1)
50
51    for qubit in range(N_len - 1):
52        qc.ccx(qubit, qubit + 1, N_len)
53
54    qc.z(N_len)
55
56    for qubit in reversed(range(N_len - 1)):
57        qc.ccx(qubit, qubit + 1, N_len)
58
59    return qc.to_gate()

An oracle which inverts the sign if the number of 11 is odd. 11 が奇数個あるなら符号を反転するオラクル