{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Quantinuum Simulators, Emulators and Quantum Hardware, via Nexus\n", "\n", "\n", "This notebook outlines how to target and configure specific simulators, emulators and quantum hardware offered by Quantinuum.\n", "\n", "[Go to Full Example H-series Workflow using qnexus](#example-h-series-workflow)\n", "\n", "For more extensive documentation on emulators and hardware, please see the [H-series documentation](https://docs.quantinuum.com/h-series)" ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [], "source": [ "import qnexus as qnx\n", "\n", "from qnexus.models.language import Language" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Available Quantinuum Devices\n", "\n", "\n", "You can select which Quantinuum device you'd like to target via the `device_name` parameter in the `QuantinuumConfig` you pass as part of a job submission.\n", "\n", "### Noiseless simulators (cloud-hosted by Nexus)\n", "\n", "These are currently provided for all Nexus users. Usage is accounted for in your Simulation quota.\n", "\n", "- \"H1-1LE\"\n", "- \"H2-1LE\"\n", "\n", "### Syntax Checkers\n", "\n", "We recommend these are used to verify your code before submission to hardware or emulators.\n", "\n", "- \"H1-1SC\"\n", "- \"H2-1SC\"\n", "\n", "### Noise-modelled Emulators\n", "\n", "These attempt to accurately emulate the H-series hardware, with configurable error models. Currently we provide both cloud-hosted emulators and emulators running on our own hardware. These both use the same underlying software with nearly-identical noise-modelling so it is expected that results are comparable.\n", "\n", "Cloud-hosted emulators require that your organisation has the 'Emulator' premium feature in Nexus, and usage is accounted for in your Simulation quota.\n", "\n", "- \"H1-Emulator\"\n", "- \"H2-Emulator\"\n", "\n", "We also offer access to emulators running on our own hardware, these each require a specific H-series Plan and usage is accounted for in HQC.\n", "\n", "- \"H1-1E\"\n", "- \"H2-1E\"\n", "\n", "### Quantum Hardware\n", "\n", "These are Quantinuum's quantum computers. They each require a specific H-series Plan and usage is accounted for in HQC.\n", "\n", "- \"H1-1\" \n", "- \"H2-1\"\n", "\n", "\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Create a configuration to target the H1-1LE noiseless simulator\n", "my_quantinuum_config = qnx.QuantinuumConfig(\n", " device_name=\"H1-1LE\",\n", ")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Calculating Cost (H-series and hardware-hosted emulators only)\n", "\n", "\n", "Nexus provides the ability to find out the cost of running circuit executions on Quantinuum quantum computers (e.g. `H1-1`) and hardware-hosted emulators (e.g. `H1-1E`). \n", "\n", "NB this is different from the cloud-hosted simulators (e.g. `H1-1LE`) or emulators (e.g. `H1-Emulator`) which are accounted for in your Simulation quota (measured in seconds), for which we do not offer cost estimation.\n", "\n", "The `syntax_checker` argument should be the corresponding syntax checker device (e.g. \"H1-1SC\" for \"H1-1E\" or \"H1-1\").\n", "\n", "```python\n", "qnx.circuits.cost(\n", " circuit_ref=your_circuit_ref,\n", " n_shots=1000,\n", " backend_config=qnx.QuantinuumConfig(device_name=\"H1-1\"),\n", " syntax_checker=\"H1-1SC\",\n", ")\n", "\n", "# -> returns a float representing the cost in HQC\n", "```\n", "\n", "\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Emulator Error Configuration\n", "\n", "By default, both the cloud-hosted (e.g. `H1-Emulator`) and hardware-hosted (e.g. `H1-1E`) emulators will model H-series quantum hardware. If desired this noise can be configured.\n", "\n", "For documentation on noise configuration, please see the [H-series emulator noise model documentation](https://docs.quantinuum.com/h-series/user_guide/emulator_user_guide/noise_model.html)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "from qnexus.models.h_series_noise import UserErrorParams\n", "\n", "my_params = UserErrorParams(\n", " p1 = 0.1,\n", " p2 = 0.5,\n", " # adjust as needed according to noise model documentation\n", ")\n", "\n", "backend_config = qnx.QuantinuumConfig(\n", " device_name=\"H1-Emulator\", # Or another emulator such as H1-1E\n", " error_params = my_params\n", ")" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Alternatively you can pass in the noise model as a dictionary\n", "backend_config = qnx.QuantinuumConfig(\n", " device_name=\"H1-Emulator\",\n", " error_params = {\"p1\":0.1, \"p2\":0.5}\n", ")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Compiler Options\n", "\n", "\n", "By default, additional compliation will NOT occur in the H-series submission stack (e.g. for quantum hardware or hardware-hosted emulators like `H1-1E`). However if desired, additional compilition can be configured.\n", "\n", "Certain compiler flags can be passed on to the compiler in the H-series submission stack. This is distinct from the TKET-based compilation that happens when you compile circuits in Nexus.\n", "\n", "You can configure compiler options in the `QuantinuumConfig` by passing `no_opt=False` and `QuantinuumCompilerOptions` as arguments.\n", "\n", "If you would like more information on the compilation configuration available, please get in touch with H-series suppport." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "from quantinuum_schemas.models.backend_config import QuantinuumCompilerOptions\n", "\n", "# Allow the H-series compiler to decide what 2-qubit gate to rebase to.\n", "compiler_flags = {\"noreduce\": True}\n", "\n", "backend_config = qnx.QuantinuumConfig(\n", " device_name=\"H1-1\",\n", " no_opt=False,\n", " compiler_options=QuantinuumCompilerOptions(**compiler_flags),\n", ")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Submission Language selection\n", "\n", "You can specify the submission language for execute job submissions to H-series, available options include `QIR`, `AUTO` and `OPENQASM 2.0`.\n", "\n", "```python\n", "execute_job_ref = qnx.start_execute_job(\n", " circuits=my_circuit_ref,\n", " name=f\"My Execute Job from {datetime.now()}\",\n", " n_shots=[100],\n", " backend_config=backend_config,\n", " project=my_project_ref,\n", " language=\"QIR\",\n", ")\n", "```" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Queueing for H-Series hardware and emulators\n", "\n", "Quantinuum Nexus is the default platform for submitting to H-series emulators and hardware, however H-series hardware and emulators have their own dedicated job queue.\n", "\n", "When you submit a job to H-series hardware or emulators, they will be entered into a fair-share queuing system. When the selected device is available the fair-share queueing algorithm will select a job approximately as follows:\n", "\n", "- Select jobs queued for active batches.\n", "- Select an Organisation that has used the device the least in recent history.\n", " - Select a job from that Organisation that was submitted under a User Group with the highest Group priority (1 being highest, 5 being default, 10 being lowest).\n", " - Select a job from that Organisation that was submitted by a User with the highest User priority (same ordering as above).\n", "\n", "\n", "Your organization admin can help assign the appropriate priority to you or a User Group you are a member of.\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Batching\n", "\n", "If you expect to run multiple circuits, or several circuits in succession (such as during a variational project) you can request that the H-series submission queue 'batches' your circuits together so they avoid queueing seperately. Circuits submitted to an existing batch will run immediately, provided they are submitted within 60 seconds of the completion of the last circuit you submitted to the batch. \n", "\n", "\n", "If desired Nexus will attempt to automatically handle the batching of circuits when submitted in a list (such as an execute job with multiple circuits) or in succession (multiple execute job submissions).\n", "\n", "You can request that Nexus attempts to batch your circuits by setting the `attempt_batching` flag in the `QuantinuumConfig`:" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "backend_config = qnx.QuantinuumConfig(\n", " device_name=\"H1-1E\", attempt_batching=True\n", ")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Example H-series workflow\n", "\n", "The following is a minimal example workflow targetting the H-series emulator `H1-1E` to compile and execute a circuit with a custom noise model configuration." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "import qnexus as qnx\n", "from pytket import Circuit\n", "from datetime import datetime" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# View Quantinuum devices that are available to the logged in user\n", "qnx.devices.get_all(issuers=[\"QUANTINUUM\"]).df()" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "my_project_ref = qnx.projects.get_or_create(name=\"My H1-1E Project\")" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Specify our config to target the H1-1E device, with a custom noise model\n", "\n", "my_params = UserErrorParams(\n", " # Linearly scale the probability of dephasing causing a fault.\n", " memory_scale = 0.5,\n", ")\n", "\n", "backend_config = qnx.QuantinuumConfig(\n", " device_name=\"H1-1E\"\n", " error_params = my_params\n", ")" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "circuit = Circuit(2).H(0).CX(0,1).measure_all()\n", "\n", "my_circuit_ref = qnx.circuits.upload(\n", " name=f\"My H-series Circuit from {datetime.now()}\",\n", " circuit = circuit,\n", " project = my_project_ref,\n", ")" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Compile the circuit on Nexus using our hosted TKET compilation service\n", "\n", "compiled_circuits = qnx.compile(\n", " circuits=[my_circuit_ref],\n", " name=f\"My Compile Job from {datetime.now()}\",\n", " optimisation_level=1,\n", " backend_config=backend_config,\n", " project=my_project_ref,\n", ")\n", "\n", "compiled_circuits.df()" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Double check the HQC cost of running the circuit\n", "execution_cost = qnx.circuits.cost(\n", " circuit_ref=compiled_circuits[0],\n", " n_shots=1000,\n", " backend_config=qnx.QuantinuumConfig(device_name=\"H1-1E\"),\n", " syntax_checker=\"H1-1SC\",\n", ")\n", "\n", "print(execution_cost)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Submit the job for execution on the H1-Emulator\n", "\n", "execute_job_ref = qnx.start_execute_job(\n", " circuits=compiled_circuits,\n", " name=f\"My Execute Job from {datetime.now()}\",\n", " n_shots=[100]* len(compiled_circuits),\n", " backend_config=backend_config,\n", " project=my_project_ref,\n", " language=Language.QIR,\n", ")\n", "\n", "execute_job_ref.df()" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "qnx.jobs.wait_for(execute_job_ref)" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "# Retrieve a ExecutionResultRef for every Circuit that was executed\n", "execute_job_result_refs = qnx.jobs.results(execute_job_ref)\n", "\n", "# Get a pytket BackendResult for the execution\n", "result = execute_job_result_refs[0].download_result()\n", "\n", "result.get_counts()" ] } ], "metadata": { "kernelspec": { "display_name": "qnexus-Rou6F43i-py3.12", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.12.5" } }, "nbformat": 4, "nbformat_minor": 2 }