Knowledge Base

Your A-Z guide of simple, bite-sized explainers to help you understand all about quantum 

This section shows a complete example of a working application. Below, all files are shown, which are generated when creating your application and experiment and its contents. You can use this example to see what a complete application and experiment looks like and see how you can apply some of the examples to your experiment.

Application

Create your application using the following command:

qne application create teleport Sender Receiver

Config

Within the config directory, you can find the application.json, network.json, and results.json. You can leave results.json as it is. Fill in application.json and network.json with the examples given below.

application.json

[
{
"title": "Qubit state of Sender",
"slug": "qubit_state_sender",
"description": "...",
"values": [
{
"name": "phi",
"default_value": 0.0,
"minimum_value": -1.0,
"maximum_value": 1.0,
"unit": "",
"scale_value": 1.0
},
{
"name": "theta",
"default_value": 0.0,
"minimum_value": 0.0,
"maximum_value": 1.0,
"unit": "",
"scale_value": 1.0
}
],
"input_type": "qubit",
"roles": [
"Sender"
]
}
]

network.json

{
"networks": [
"randstad",
"europe",
"the-netherlands"
],
"roles": [
"Sender",
"Receiver"
]
}

Src

After creating your application, a src directory has also been created containing the files app_sender.py and app_receiver.py. Below two examples are given, which you can use to fill in these files.

app_sender.py

import math

from netqasm.logging.output import get_new_app_logger
from netqasm.sdk import EPRSocket, Qubit
from netqasm.sdk.classical_communication.message import StructuredMessage
from netqasm.sdk.external import NetQASMConnection, Socket
from netqasm.sdk.toolbox import set_qubit_state


def main(app_config=None, phi=0.0, theta=0.0):
phi *= math.pi
theta *= math.pi

log_config = app_config.log_config
app_logger = get_new_app_logger(app_name="sender", log_config=log_config)

# Create a socket to send classical information
socket = Socket("sender", "receiver", log_config=log_config)

# Create a EPR socket for entanglement generation
epr_socket = EPRSocket("receiver")

print("`sender` will start to teleport a qubit to `receiver`")

# Initialize the connection to the backend
sender = NetQASMConnection(
app_name=app_config.app_name, log_config=log_config, epr_sockets=[epr_socket]
)
with sender:
# Create a qubit to teleport
q = Qubit(sender)
set_qubit_state(q, phi, theta)

# Create EPR pairs
epr = epr_socket.create()[0]

# Teleport
q.cnot(epr)
q.H()
m1 = q.measure()
m2 = epr.measure()

# Send the correction information
m1, m2 = int(m1), int(m2)

app_logger.log(f"m1 = {m1}")
app_logger.log(f"m2 = {m2}")
print(
f"`sender` measured the following teleportation corrections: m1 = {m1}, m2 = {m2}"
)
print("`sender` will send the corrections to `receiver`")

socket.send_structured(StructuredMessage("Corrections", (m1, m2)))

socket.send_silent(str((phi, theta)))

return {"m1": m1, "m2": m2}


if __name__ == "__main__":
main()

app_receiver.py

from netqasm.sdk import EPRSocket
from netqasm.sdk.external import NetQASMConnection, Socket, get_qubit_state
from netqasm.sdk.toolbox.sim_states import get_fidelity, qubit_from, to_dm


def main(app_config=None):
log_config = app_config.log_config

# Create a socket to recv classical information
socket = Socket("receiver", "sender", log_config=log_config)

# Create a EPR socket for entanglement generation
epr_socket = EPRSocket("sender")

# Initialize the connection
receiver = NetQASMConnection(
app_name=app_config.app_name, log_config=log_config, epr_sockets=[epr_socket]
)
with receiver:
epr = epr_socket.recv()[0]
receiver.flush()

# Get the corrections
m1, m2 = socket.recv_structured().payload
print(f"`receiver` got corrections: {m1}, {m2}")
if m2 == 1:
print("`receiver` will perform X correction")
epr.X()
if m1 == 1:
print("`receiver` will perform Z correction")
epr.Z()

receiver.flush()
# Get the qubit state
# NOTE only possible in simulation, not part of actual application
dm = get_qubit_state(epr)
print(f"`receiver` recieved the teleported state {dm}")

# Reconstruct the original qubit to compare with the received one
# NOTE only to check simulation results, normally the Sender does not
# need to send the phi and theta values!
msg = socket.recv_silent() # don't log this
phi, theta = eval(msg)

original = qubit_from(phi, theta)
original_dm = to_dm(original)
fidelity = get_fidelity(original, dm)

return {
"original_state": original_dm.tolist(),
"correction1": "Z" if m1 == 1 else "None",
"correction2": "X" if m2 == 1 else "None",
"received_state": dm.tolist(),
"fidelity": fidelity,
}


if __name__ == "__main__":
main()

Experiment

Create your experiment using the following command:

qne experiment create teleport_experiment teleport randstad

Input

After executing the experiment create command, an input directory is created within the experiment directory. These files are all copied over from the teleport application and can be left untouched. 

experiment.json

Next to the input that is generated, an experiment.json file is generated as well. This is where you can choose which nodes to use for your roles and give your inputs a specific value. Below is an entire experiment.json file as an example. Use the contents of this example in your experiment.json file.

{
"meta": {
    "application": {
      "slug": "teleport",
      "app_version": "",
      "multi_round": false
    },
      "backend": {
      "location": "local",
      "type": "local_netsquid"
    },
    "number_of_rounds": 1,
    "description": "teleport_experiment: experiment description",
    "name": "teleport_experiment"
  },
"asset": {
"network": {
"name": "Randstad",
"slug": "randstad",
"channels": [
{
"slug": "amsterdam-leiden",
"node1": "amsterdam",
"node2": "leiden",
"parameters": [
{
"slug": "elementary-link-fidelity",
"values": [
{
"name": "fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
]
},
{
"slug": "leiden-the-hague",
"node1": "leiden",
"node2": "the-hague",
"parameters": [
{
"slug": "elementary-link-fidelity",
"values": [
{
"name": "fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
]
},
{
"slug": "delft-the-hague",
"node1": "delft",
"node2": "the-hague",
"parameters": [
{
"slug": "elementary-link-fidelity",
"values": [
{
"name": "fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
]
},
{
"slug": "delft-rotterdam",
"node1": "delft",
"node2": "rotterdam",
"parameters": [
{
"slug": "elementary-link-fidelity",
"values": [
{
"name": "fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
]
}
],
"nodes": [
{
"name": "Amsterdam",
"slug": "amsterdam",
"coordinates": {
"latitude": 52.3667,
"longitude": 4.8945
},
"node_parameters": [
{
"slug": "gate-fidelity",
"values": [
{
"name": "gate_fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
],
"qubits": [
{
"qubit_id": 0,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 1,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 2,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
}
]
},
{
"name": "Leiden",
"slug": "leiden",
"coordinates": {
"latitude": 52.1601,
"longitude": 4.497
},
"node_parameters": [
{
"slug": "gate-fidelity",
"values": [
{
"name": "gate_fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
],
"qubits": [
{
"qubit_id": 0,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 1,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 2,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
}
]
},
{
"name": "The Hague",
"slug": "the-hague",
"coordinates": {
"latitude": 52.0705,
"longitude": 4.3007
},
"node_parameters": [
{
"slug": "gate-fidelity",
"values": [
{
"name": "gate_fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
],
"qubits": [
{
"qubit_id": 0,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 1,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 2,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
}
]
},
{
"name": "Delft",
"slug": "delft",
"coordinates": {
"latitude": 52.0116,
"longitude": 4.3571
},
"node_parameters": [
{
"slug": "gate-fidelity",
"values": [
{
"name": "gate_fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
],
"qubits": [
{
"qubit_id": 0,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 1,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 2,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
}
]
},
{
"name": "Rotterdam",
"slug": "rotterdam",
"coordinates": {
"latitude": 51.9244,
"longitude": 4.4777
},
"node_parameters": [
{
"slug": "gate-fidelity",
"values": [
{
"name": "gate_fidelity",
"value": 1.0,
"scale_value": 1.0
}
]
}
],
"qubits": [
{
"qubit_id": 0,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 1,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
},
{
"qubit_id": 2,
"qubit_parameters": [
{
"slug": "relaxation-time",
"values": [
{
"name": "t1",
"value": 0,
"scale_value": 1.0
}
]
},
{
"slug": "dephasing-time",
"values": [
{
"name": "t2",
"value": 0,
"scale_value": 1.0
}
]
}
]
}
]
}
],
"roles": {
"Sender": "amsterdam",
"Receiver": "leiden"
}
},
"application": [
{
"roles": [
"Sender"
],
"values": [
{
"name": "phi",
"value": 0.7,
"scale_value": 1.0
},
{
"name": "theta",
"value": 0.3,
"scale_value": 1.0
}
]
}
]
}
}

Run your experiment

After you have created your experiment and modified the contents of experiment.json, you can run your experiment with the following command:

qne experiment run

This will generate some raw outputs in your experiment directory and a processed.json file where all the results of your experiment are stored!

Examine experiment results

qne experiment results --all

Results of latest run are stored in processed.json

qne experiment results --show

The result from processed.json is shown on the terminal.