Spaces:
Runtime error
Runtime error
BoltzmannEntropy
commited on
Commit
·
41e6c53
1
Parent(s):
334036d
Co
Browse files- Dockerfile +1 -1
- app.py +48 -38
Dockerfile
CHANGED
|
@@ -85,7 +85,7 @@ COPY --chown=user:user app.py .
|
|
| 85 |
# COPY --chown=user:user test_images /home/user/app/test_images
|
| 86 |
|
| 87 |
ENV PYTHONUNBUFFERED=1 GRADIO_ALLOW_FLAGGING=never GRADIO_NUM_PORTS=1 GRADIO_SERVER_NAME=0.0.0.0 GRADIO_SERVER_PORT=7860 SYSTEM=spaces
|
| 88 |
-
RUN python3 -m pip install pennylane sympy pennylane-qiskit duckdb
|
| 89 |
WORKDIR $HOME/app
|
| 90 |
|
| 91 |
EXPOSE 8097 7842 8501 8000 6666 7860
|
|
|
|
| 85 |
# COPY --chown=user:user test_images /home/user/app/test_images
|
| 86 |
|
| 87 |
ENV PYTHONUNBUFFERED=1 GRADIO_ALLOW_FLAGGING=never GRADIO_NUM_PORTS=1 GRADIO_SERVER_NAME=0.0.0.0 GRADIO_SERVER_PORT=7860 SYSTEM=spaces
|
| 88 |
+
RUN python3 -m pip install pennylane sympy pennylane-qiskit duckdb qutip qutip-qip
|
| 89 |
WORKDIR $HOME/app
|
| 90 |
|
| 91 |
EXPOSE 8097 7842 8501 8000 6666 7860
|
app.py
CHANGED
|
@@ -10,33 +10,20 @@ import matplotlib.pyplot as plt
|
|
| 10 |
from PIL import Image
|
| 11 |
import pennylane as qml
|
| 12 |
import base64
|
| 13 |
-
|
| 14 |
-
from numpy import pi
|
| 15 |
-
import numpy as np
|
| 16 |
from qutip import *
|
| 17 |
from qutip.qip.operations import *
|
| 18 |
from qutip.qip.circuit import QubitCircuit, Gate
|
|
|
|
|
|
|
| 19 |
|
| 20 |
-
# Define a device
|
| 21 |
dev = qml.device('default.qubit', wires=10)
|
| 22 |
|
| 23 |
-
def plot_qutip_circuit():
|
| 24 |
-
q = QubitCircuit(2, reverse_states=False)
|
| 25 |
-
q.add_gate("CNOT", controls=[0], targets=[1])
|
| 26 |
-
|
| 27 |
-
# Display the circuit as an image
|
| 28 |
-
q.png # Generates and renders the circuit diagram
|
| 29 |
-
|
| 30 |
-
return q
|
| 31 |
-
|
| 32 |
-
|
| 33 |
# Hugging Face and DuckDB function placeholders
|
| 34 |
def store_in_hf_dataset(data):
|
| 35 |
-
# Implement storing data in the Hugging Face dataset
|
| 36 |
pass
|
| 37 |
|
| 38 |
def load_from_hf_dataset():
|
| 39 |
-
# Implement loading data from the Hugging Face dataset
|
| 40 |
return []
|
| 41 |
|
| 42 |
# Function to buffer the plot and return as PIL image
|
|
@@ -52,6 +39,13 @@ def pil_image_to_bytes(image):
|
|
| 52 |
image.save(img_byte_arr, format='PNG')
|
| 53 |
return img_byte_arr.getvalue()
|
| 54 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 55 |
# Function to generate a random Hamiltonian
|
| 56 |
def generate_random_hamiltonian(num_qubits):
|
| 57 |
terms = []
|
|
@@ -88,20 +82,24 @@ def hamiltonian_to_qasm(hamiltonian, num_qubits):
|
|
| 88 |
|
| 89 |
return qasm_code
|
| 90 |
|
| 91 |
-
# Function
|
| 92 |
-
def
|
| 93 |
-
|
| 94 |
-
|
| 95 |
|
| 96 |
-
|
| 97 |
-
|
| 98 |
-
|
| 99 |
-
|
| 100 |
-
|
| 101 |
-
|
| 102 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 103 |
|
| 104 |
-
return
|
| 105 |
|
| 106 |
# Store data in DuckDB
|
| 107 |
def store_in_duckdb(data, db_file='quantum_hamiltonians.duckdb'):
|
|
@@ -120,13 +118,7 @@ def store_in_duckdb(data, db_file='quantum_hamiltonians.duckdb'):
|
|
| 120 |
VALUES (?, ?, ?, ?, ?, ?, ?, ?)""", data)
|
| 121 |
conn.close()
|
| 122 |
|
| 123 |
-
#
|
| 124 |
-
def encode_image_from_blob(blob):
|
| 125 |
-
img_buffer = io.BytesIO(blob)
|
| 126 |
-
image = Image.open(img_buffer)
|
| 127 |
-
img_str = base64.b64encode(img_buffer.getvalue()).decode("utf-8")
|
| 128 |
-
return f'<img src="data:image/png;base64,{img_str}" style="max-width:500px;"/>'
|
| 129 |
-
|
| 130 |
def load_from_duckdb(db_file='quantum_hamiltonians.duckdb'):
|
| 131 |
conn = duckdb.connect(database=db_file)
|
| 132 |
df = conn.execute("SELECT * FROM hamiltonians").df()
|
|
@@ -185,9 +177,11 @@ def generate_hamiltonians(num_hamiltonians, selected_qubits, selected_order, wri
|
|
| 185 |
qasm_code = hamiltonian_to_qasm(hamiltonian, num_qubits)
|
| 186 |
trotter_code = trotter_decomposition(hamiltonian, order)
|
| 187 |
|
| 188 |
-
#
|
| 189 |
-
|
| 190 |
-
|
|
|
|
|
|
|
| 191 |
circuit_plot_image = buffer_plot_and_get(fig)
|
| 192 |
circuit_plot_bytes = pil_image_to_bytes(circuit_plot_image)
|
| 193 |
|
|
@@ -209,6 +203,22 @@ def load_results(load_from_hf, load_from_duckdb1):
|
|
| 209 |
if load_from_duckdb1:
|
| 210 |
return load_from_duckdb()
|
| 211 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 212 |
# Gradio app
|
| 213 |
with gr.Blocks() as app:
|
| 214 |
gr.Markdown("# Quantum Hamiltonian Generator")
|
|
|
|
| 10 |
from PIL import Image
|
| 11 |
import pennylane as qml
|
| 12 |
import base64
|
|
|
|
|
|
|
|
|
|
| 13 |
from qutip import *
|
| 14 |
from qutip.qip.operations import *
|
| 15 |
from qutip.qip.circuit import QubitCircuit, Gate
|
| 16 |
+
import pennylane as qml
|
| 17 |
+
from math import pi
|
| 18 |
|
| 19 |
+
# Define a Pennylane device
|
| 20 |
dev = qml.device('default.qubit', wires=10)
|
| 21 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 22 |
# Hugging Face and DuckDB function placeholders
|
| 23 |
def store_in_hf_dataset(data):
|
|
|
|
| 24 |
pass
|
| 25 |
|
| 26 |
def load_from_hf_dataset():
|
|
|
|
| 27 |
return []
|
| 28 |
|
| 29 |
# Function to buffer the plot and return as PIL image
|
|
|
|
| 39 |
image.save(img_byte_arr, format='PNG')
|
| 40 |
return img_byte_arr.getvalue()
|
| 41 |
|
| 42 |
+
# Encode the image in base64 to display in HTML
|
| 43 |
+
def encode_image_from_blob(blob):
|
| 44 |
+
img_buffer = io.BytesIO(blob)
|
| 45 |
+
image = Image.open(img_buffer)
|
| 46 |
+
img_str = base64.b64encode(img_buffer.getvalue()).decode("utf-8")
|
| 47 |
+
return f'<img src="data:image/png;base64,{img_str}" style="max-width:500px;"/>'
|
| 48 |
+
|
| 49 |
# Function to generate a random Hamiltonian
|
| 50 |
def generate_random_hamiltonian(num_qubits):
|
| 51 |
terms = []
|
|
|
|
| 82 |
|
| 83 |
return qasm_code
|
| 84 |
|
| 85 |
+
# Function to parse QASM code and create Pennylane circuit
|
| 86 |
+
def qasm_to_pennylane(qasm_code):
|
| 87 |
+
qasm_lines = qasm_code.split("\n")
|
| 88 |
+
num_qubits = int(qasm_lines[2].split('[')[1].split(']')[0]) # Extract number of qubits from QASM
|
| 89 |
|
| 90 |
+
@qml.qnode(dev)
|
| 91 |
+
def circuit():
|
| 92 |
+
for line in qasm_lines:
|
| 93 |
+
if "x" in line:
|
| 94 |
+
qml.PauliX(int(line.split('q[')[1].split(']')[0]))
|
| 95 |
+
elif "rz" in line:
|
| 96 |
+
angle = float(line.split('(')[1].split(')')[0])
|
| 97 |
+
qml.RZ(angle, int(line.split('q[')[1].split(']')[0]))
|
| 98 |
+
elif "ry" in line:
|
| 99 |
+
qml.RY(pi / 2, int(line.split('q[')[1].split(']')[0]))
|
| 100 |
+
return qml.state()
|
| 101 |
|
| 102 |
+
return circuit
|
| 103 |
|
| 104 |
# Store data in DuckDB
|
| 105 |
def store_in_duckdb(data, db_file='quantum_hamiltonians.duckdb'):
|
|
|
|
| 118 |
VALUES (?, ?, ?, ?, ?, ?, ?, ?)""", data)
|
| 119 |
conn.close()
|
| 120 |
|
| 121 |
+
# Function to load results from DuckDB
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 122 |
def load_from_duckdb(db_file='quantum_hamiltonians.duckdb'):
|
| 123 |
conn = duckdb.connect(database=db_file)
|
| 124 |
df = conn.execute("SELECT * FROM hamiltonians").df()
|
|
|
|
| 177 |
qasm_code = hamiltonian_to_qasm(hamiltonian, num_qubits)
|
| 178 |
trotter_code = trotter_decomposition(hamiltonian, order)
|
| 179 |
|
| 180 |
+
# Generate Pennylane circuit from QASM code
|
| 181 |
+
circuit = qasm_to_pennylane(qasm_code)
|
| 182 |
+
|
| 183 |
+
# Draw the Pennylane circuit and save as an image
|
| 184 |
+
fig, ax = qml.draw_mpl(circuit)()
|
| 185 |
circuit_plot_image = buffer_plot_and_get(fig)
|
| 186 |
circuit_plot_bytes = pil_image_to_bytes(circuit_plot_image)
|
| 187 |
|
|
|
|
| 203 |
if load_from_duckdb1:
|
| 204 |
return load_from_duckdb()
|
| 205 |
|
| 206 |
+
# Function for Trotter decomposition
|
| 207 |
+
def trotter_decomposition(hamiltonian, order):
|
| 208 |
+
terms = hamiltonian.split(" + ")
|
| 209 |
+
trotter_steps = []
|
| 210 |
+
|
| 211 |
+
for term in terms:
|
| 212 |
+
coeff, *pauli_ops = term.split(" * ")
|
| 213 |
+
coeff = float(coeff)
|
| 214 |
+
for _ in range(order):
|
| 215 |
+
trotter_steps.append(f"exp({coeff / order}) * ({' * '.join(pauli_ops)})")
|
| 216 |
+
for _ in range(order):
|
| 217 |
+
trotter_steps.append(f"exp({-coeff / order}) * ({' * '.join(pauli_ops)})")
|
| 218 |
+
|
| 219 |
+
return " + ".join(trotter_steps)
|
| 220 |
+
|
| 221 |
+
|
| 222 |
# Gradio app
|
| 223 |
with gr.Blocks() as app:
|
| 224 |
gr.Markdown("# Quantum Hamiltonian Generator")
|