Enabled readthedocs for Intel QS (#40)

* Added markdown with Sphinx
Added .md and .rst into the markdown parser

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Added CONTRIBUTING.md

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Restructuring the project

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Added ipynb source

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Pushing requirements.txt

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Remove the pkg-resources: bug

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Added one more example and fixed the title for GST

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Fixed title again

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Fixing titles for getting started

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Fixing ipynb title

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Added Exhale, Breathe for Doxygen support

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Remove the bug again

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Fixed the relative path for doxygen

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Updated the gitignore to ignore output from doxygen

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Fixed section title and ipynb title

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Finally fixed Example 1 and Example 2 markdown to show up

Signed-off-by: Stanley Phoong <stanley.cheong.kwan.phoong@intel.com>

* Update import_iqs.py

update the syntax of init and finalize functions for the MPI environment

* Update python_build_no_mpi.yml

test of new workflow to setup Miniconda

* Update python_build_mpi.yml

Co-authored-by: giangiac <30329377+giangiac@users.noreply.github.com>
This commit is contained in:
Stanley 2020-11-19 00:16:44 +08:00 committed by GitHub
parent b2944cd2ac
commit 22446d4df0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
13 changed files with 1256 additions and 4 deletions

View File

@ -16,7 +16,7 @@ jobs:
# Steps represent a sequence of tasks that will be executed as part of the job
steps:
- uses: goanpeca/setup-miniconda@v1
- uses: conda-incubator/setup-miniconda@v2
with:
auto-update-conda: true
python-version: 3.7

View File

@ -16,7 +16,7 @@ jobs:
# Steps represent a sequence of tasks that will be executed as part of the job
steps:
- uses: goanpeca/setup-miniconda@v1
- uses: conda-incubator/setup-miniconda@v2
with:
auto-update-conda: true
python-version: 3.7

6
.gitignore vendored
View File

@ -1,2 +1,8 @@
*.o
**/libintel_qs.a
docs/source/_static
docs/source/_templates
docs/build
venv
docs/source/doxyoutput
docs/source/api

20
docs/Makefile Normal file
View File

@ -0,0 +1,20 @@
# Minimal makefile for Sphinx documentation
#
# You can set these variables from the command line, and also
# from the environment for the first two.
SPHINXOPTS ?=
SPHINXBUILD ?= sphinx-build
SOURCEDIR = source
BUILDDIR = build
# Put it first so that "make" without argument is like "make help".
help:
@$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)
.PHONY: help Makefile
# Catch-all target: route all unknown targets to Sphinx using the new
# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS).
%: Makefile
@$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O)

35
docs/make.bat Normal file
View File

@ -0,0 +1,35 @@
@ECHO OFF
pushd %~dp0
REM Command file for Sphinx documentation
if "%SPHINXBUILD%" == "" (
set SPHINXBUILD=sphinx-build
)
set SOURCEDIR=source
set BUILDDIR=build
if "%1" == "" goto help
%SPHINXBUILD% >NUL 2>NUL
if errorlevel 9009 (
echo.
echo.The 'sphinx-build' command was not found. Make sure you have Sphinx
echo.installed, then set the SPHINXBUILD environment variable to point
echo.to the full path of the 'sphinx-build' executable. Alternatively you
echo.may add the Sphinx directory to PATH.
echo.
echo.If you don't have Sphinx installed, grab it from
echo.http://sphinx-doc.org/
exit /b 1
)
%SPHINXBUILD% -M %1 %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O%
goto end
:help
%SPHINXBUILD% -M help %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O%
:end
popd

59
docs/requirements.txt Normal file
View File

@ -0,0 +1,59 @@
alabaster==0.7.12
async-generator==1.10
attrs==20.2.0
Babel==2.8.0
beautifulsoup4==4.9.3
bleach==3.2.1
breathe==4.23.0
bs4==0.0.1
certifi==2020.6.20
chardet==3.0.4
commonmark==0.9.1
decorator==4.4.2
defusedxml==0.6.0
docutils==0.16
entrypoints==0.3
idna==2.10
imagesize==1.2.0
importlib-metadata==2.0.0
ipython-genutils==0.2.0
Jinja2==2.11.2
jsonschema==3.2.0
jupyter-client==6.1.7
jupyter-core==4.6.3
jupyterlab-pygments==0.1.2
lxml==4.6.1
MarkupSafe==1.1.1
mistune==0.8.4
nbclient==0.5.1
nbconvert==6.0.7
nbformat==5.0.8
nbsphinx==0.8.0
nest-asyncio==1.4.2
packaging==20.4
pandocfilters==1.4.3
Pygments==2.7.2
pyparsing==2.4.7
pyrsistent==0.17.3
python-dateutil==2.8.1
pytz==2020.1
pyzmq==19.0.2
recommonmark==0.6.0
requests==2.24.0
six==1.15.0
snowballstemmer==2.0.0
soupsieve==2.0.1
Sphinx==3.2.1
sphinxcontrib-applehelp==1.0.2
sphinxcontrib-devhelp==1.0.2
sphinxcontrib-htmlhelp==1.0.3
sphinxcontrib-jsmath==1.0.1
sphinxcontrib-qthelp==1.0.3
sphinxcontrib-serializinghtml==1.1.4
testpath==0.4.4
tornado==6.0.4
traitlets==4.3.3
urllib3==1.25.11
webencodings==0.5.1
zipp==3.4.0
exhale==0.2.3

View File

@ -0,0 +1,20 @@
# Contributing
Thanks for your interest in the project!
Any contribution, project participation and pull request from developers are welcome. Please follow this process:
* Clone this repository or fork it. Create a new branch and add your modifications.
* Remember to add unit tests to verify the desired behavior of the new features or methods.
* When the first version of the code is ready, create a pull-request to the **development** branch of `iqusoft/intel-qs`.
* Edits may be required to resolve conflicts since it is possible that the repository has changed while you worked on your new contribution.
Please resolve the merge conflicts.
* Verify that all unit tests, and not only the one added in the contribution, run correctly.
* The IQS team will help with the revision of the pull-request.
To facilitate the review consider starting with small contributions (a couple files and ~100 lines).
For contributions that require substantial changes or changes in many files, please contact the IQS team to discuss the most effective strategy.
Creating your pull request from a fork? We suggest allowing edits from maintainers. Then, anyone with Write access to the upstream repository will be able to add commits to your branch. This can make the review process easier for maintainers since they can make a small change themselves instead of asking you to make the change.
If you would like to contribute to IQS, please visit our wiki page [https://github.com/iqusoft/intel-qs/wiki/Contribute](https://github.com/iqusoft/intel-qs/wiki/Contribute).

83
docs/source/conf.py Normal file
View File

@ -0,0 +1,83 @@
# Configuration file for the Sphinx documentation builder.
#
# This file only contains a selection of the most common options. For a full
# list see the documentation:
# https://www.sphinx-doc.org/en/master/usage/configuration.html
# -- Path setup --------------------------------------------------------------
# If extensions (or modules to document with autodoc) are in another directory,
# add these directories to sys.path here. If the directory is relative to the
# documentation root, use os.path.abspath to make it absolute, like shown here.
#
# import os
# import sys
# sys.path.insert(0, os.path.abspath('.'))
# -- Project information -----------------------------------------------------
project = 'Intel QS'
copyright = '2020, Intel'
author = 'Intel'
# -- General configuration ---------------------------------------------------
# Add any Sphinx extension module names here, as strings. They can be
# extensions coming with Sphinx (named 'sphinx.ext.*') or your custom
# ones.
extensions = ['recommonmark', 'nbsphinx', 'breathe', 'exhale']
# Add any paths that contain templates here, relative to this directory.
templates_path = ['_templates']
# List of patterns, relative to source directory, that match files and
# directories to ignore when looking for source files.
# This pattern also affects html_static_path and html_extra_path.
exclude_patterns = []
# -- Options for HTML output -------------------------------------------------
# The theme to use for HTML and HTML Help pages. See the documentation for
# a list of builtin themes.
#
html_theme = 'default'
# Add any paths that contain custom static files (such as style sheets) here,
# relative to this directory. They are copied after the builtin static files,
# so a file named "default.css" will overwrite the builtin "default.css".
html_static_path = ['_static']
source_parsers = {
'.md': 'recommonmark.parser.CommonMarkParser',
}
source_suffix = ['.rst', '.md']
# Setup the breathe extension
breathe_projects = {
"My Project": "./doxyoutput/xml"
}
breathe_default_project = "My Project"
# Setup the exhale extension
exhale_args = {
# These arguments are required
"containmentFolder": "./api",
"rootFileName": "library_root.rst",
"rootFileTitle": "API References",
"doxygenStripFromPath": "..",
# Suggested optional arguments
"createTreeView": True,
# TIP: if using the sphinx-bootstrap-theme, you need
# "treeViewIsBootstrap": True,
"exhaleExecutesDoxygen": True,
"exhaleDoxygenStdin": "INPUT = ../../include"
}
# Tell sphinx what the primary language being documented is.
primary_domain = 'cpp'
# Tell sphinx what the pygments highlight language should be.
highlight_language = 'cpp'

View File

@ -0,0 +1,475 @@
{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Getting started with Intel Quantum Simulator: Examples\n",
"Tutorial on the basic use of Intel QS through its Python interface: Two examples are provided.\n",
"\n",
"**NOTE:**\n",
"Currently, the Python implementation only allows for single-core execution and does not take advantages of the MPI protocol.\n",
"However the user can familiarize with the same functionalities available in the distributed implementation (only C++ at the moment) and the transition should be relatively straighforward since all methods maintain name and effect."
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"----\n",
"## Import Intel QS library\n",
"Let's start by importing the Python library with the class and methods defined in the C++ implementation."
]
},
{
"cell_type": "code",
"execution_count": 2,
"metadata": {
"hideCode": false,
"hidePrompt": false,
"scrolled": true,
"slideshow": {
"slide_type": "-"
}
},
"outputs": [],
"source": [
"# Import the Python library with the C++ class and methods of Intel Quantum Simulator.\n",
"# If the library is not contained in the same folder of this notebook, its path has to be added.\n",
"import sys\n",
"sys.path.insert(0, '../lib_python')\n",
"import intelqs as simulator\n",
"\n",
"# Import NumPy library with Intel specialization.\n",
"import numpy as np\n",
"from numpy import random_intel\n",
"\n",
"# Import graphical library for plots.\n",
"import matplotlib.pyplot as plt"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Example 1\n"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Create the state of a quantum register, having $N>3$ qubits.\n",
"\n",
"The state is initialized as a computational basis state (using the keyword \"base\") corresponding to the index 0.\n",
"\n",
"The index corresponds to a $N$-bit integer in decimal representation.\n",
"With $N$ qubits there are $2^N$ indices, from 0 to $2^{N-1}$."
]
},
{
"cell_type": "code",
"execution_count": 3,
"metadata": {},
"outputs": [],
"source": [
"# Allocate memory for the quantum register's state and initialize it to |000...0>.\n",
"num_qubits = 4;\n",
"if num_qubits<3:\n",
" num_qubits = 4;\n",
"psi1 = simulator.QubitRegister(num_qubits, \"base\", 0, 0);"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Let us apply a X Pauli gate on qubit 0, effectively flipping it from |0> to |1>, followed by the Hadamard gate on all other qubits."
]
},
{
"cell_type": "code",
"execution_count": 4,
"metadata": {},
"outputs": [],
"source": [
"# Let us apply a X Pauli gate on qubit 0, effectively flipping it from |0> to |1>.\n",
"psi1.ApplyPauliX(0);\n",
"\n",
"# Let us apply an Hadamard gate on all other qubits.\n",
"for q in range(1,num_qubits):\n",
" psi1.ApplyHadamard(q);"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"In addition to one-qubit gates, universal quantum computation can be achieved via 2-qubit entangling gates.\n",
"For example, we now apply a CNOT between qubit 2 (here the control qubit) and qubit 1 (target qubit)."
]
},
{
"cell_type": "code",
"execution_count": 5,
"metadata": {},
"outputs": [],
"source": [
"# Two qubit gates are applied in a similar way. For example, a C-NOT between qubit 2 (control qubit) and qubit 1 (target qubit):\n",
"control = 2;\n",
"target = 1;\n",
"psi1.ApplyCPauliX( control , target );"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"To extract information from the quantum register, one can obtain the probability of measuring a certain qubit in the computational basis and obtaining the outcome \"1\" (meaning that the state is in |1>). In this example we measure qubit 1.\n",
"Once the probability is known, one can draw a random number to simulate the stochastic outcome of the measurement and collapse the wavefunction accordingly."
]
},
{
"cell_type": "code",
"execution_count": 7,
"metadata": {
"hidePrompt": true
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Probability that qubit 1, if measured, is in state |1> = 0.0\n",
"\n",
"Simulated outcome is 0. Collapse the function accordingly.\n"
]
}
],
"source": [
"# Compute the probability of qubit 1 being in state |1>.\n",
"measured_qubit = 1;\n",
"prob = psi1.GetProbability( measured_qubit );\n",
"\n",
"print(\"Probability that qubit {}, if measured, is in state |1> = {}\\n\".format(measured_qubit, prob));\n",
"\n",
"# Draw random number in [0,1)\n",
"r = np.random.rand()\n",
"if r < prob:\n",
" # Collapse the wavefunction according to qubit 1 being in |1>.\n",
" print(\"Simulated outcome is 1. Collapse the function accordingly.\")\n",
" psi1.CollapseQubit(measured_qubit,True);\n",
"else:\n",
" # Collapse the wavefunction according to qubit 1 being in |0>\n",
" print(\"Simulated outcome is 0. Collapse the function accordingly.\")\n",
" psi1.CollapseQubit(measured_qubit,False);\n",
"\n",
"# In both cases one needs to re-normalize the wavefunction:\n",
"psi1.Normalize();"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Example 2\n"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Create the state of a quantum register, having $N>3$ qubits.\n",
"\n",
"The state is initialized as a random state (using the keyword \"rand\"):\n",
"\n",
"This requires a random number generator (RNG), that we initialize just before the second register. Notice that '777' plays the role of the seed to initialize the RNG."
]
},
{
"cell_type": "code",
"execution_count": 8,
"metadata": {},
"outputs": [],
"source": [
"num_qubits = 4;\n",
"if num_qubits<3:\n",
" num_qubits = 4;\n",
"psi2 = simulator.QubitRegister(num_qubits, \"rand\", 777, 0);"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Let us apply one- and two-qubit gates as in the previous exmaple."
]
},
{
"cell_type": "code",
"execution_count": 9,
"metadata": {},
"outputs": [],
"source": [
"# Let us apply a X Pauli gate on qubit 0, effectively flipping it from |0> to |1>.\n",
"psi2.ApplyPauliX(0);\n",
"\n",
"# Let us apply an Hadamard gate on all other qubits.\n",
"for q in range(1,num_qubits):\n",
" psi2.ApplyHadamard(q);"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"One can define an arbitrary single-qubit gate and apply it to the chosen qubit.\n",
"\n",
"In addition one can apply a custom one-qubit gate conditionally on the state of a control qubit."
]
},
{
"cell_type": "code",
"execution_count": 10,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"<<the output has been redirected to the terminal>>\n"
]
}
],
"source": [
"# Define an arbitrary single qubit gate and apply it to the chosen qubit.\n",
"# The quantum gate G is given by a 2x2 unitary matrix, here using a bi-dimensional NumPy array.\n",
"G = np.zeros((2,2),dtype=np.complex_);\n",
"G[0,0] = 0.592056606032915 + 0.459533060553574j;\n",
"G[0,1] = -0.314948020757856 - 0.582328159830658j;\n",
"G[1,0] = 0.658235557641767 + 0.070882241549507j;\n",
"G[1,1] = 0.649564427121402 + 0.373855203932477j;\n",
"\n",
"qubit = 0;\n",
"psi2.Apply1QubitGate(qubit,G);\n",
"\n",
"# It is also possible to apply the arbitrary gate specified by G controlled on the state of another qubit.\n",
"# G is applied conditioned on the control qubit being in |1>.\n",
"control = 1;\n",
"target = 2;\n",
"psi2.ApplyControlled1QubitGate( control, target, G);\n",
"\n",
"# Notice that this output is directed to the terminal and not re-directed to the iPython notebook.\n",
"psi2.Print(\"After all gates.\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"To extract information from the quantum register, one can obtain the expectation value of Pauli strings.\n",
"\n",
"For example, consider the Pauli string given by: $$X_0 \\otimes id_1 \\otimes Z_2 \\otimes Y_3$$\n",
"\n",
"Such observable is defined by:\n",
"- the position of the non-trivial Pauli matrices, in this case {0,2,3}\n",
"- the corresponding Pauli matrices (X=1, Y=2, Z=3).\n",
"\n",
"To facilitate the verification of the expectation value, we reinitialize the quantum state to |+-01>.\n",
"\n",
"We also consider the Pauli staing $$X_0 \\otimes id_1 \\otimes Z_2 \\otimes Z_3$$."
]
},
{
"cell_type": "code",
"execution_count": 12,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Probability that qubit 0, if measured, is in state |1> = 0.0\n",
"\n",
"Probability that qubit 1, if measured, is in state |1> = 1.0\n",
"\n",
"Probability that qubit 2, if measured, is in state |1> = 0.0\n",
"\n",
"Probability that qubit 3, if measured, is in state |1> = 1.0\n",
"\n",
"Expectation value <+-01|X_0.id_1.Z_2.Y_3|+-01> = 0.0\n",
"\n",
"Expectation value <+-01|X_0.id_1.Z_2.Z_3|+-01> = -0.9999999999999989\n",
"\n",
"Expectation value <+-01|X_0|+-01> = 1.0\n",
"\n",
"Expectation value <+-01|X_0.Z_3|+-01> = -1.0000000000000004\n",
"\n"
]
}
],
"source": [
"# Prepare the state |+-01>\n",
"index = 2+8;\n",
"psi2.Initialize(\"base\",index);\n",
"# Notice that GetProbability() does not change the state.\n",
"for qubit in range(0,num_qubits):\n",
" prob = psi2.GetProbability( qubit );\n",
" print(\"Probability that qubit {}, if measured, is in state |1> = {}\\n\".format(qubit, prob));\n",
"\n",
"psi2.ApplyHadamard(0);\n",
"psi2.ApplyHadamard(1);\n",
"\n",
"# The Pauli string given by: X_0 . id_1 . Z_2 . Y_3\n",
"# Such observable is defined by the position of the non-trivial Pauli matrices:\n",
"qubits_to_be_measured = [0,2,3]\n",
"\n",
"# And by the corresponding Pauli matrices (X=1, Y=2, Z=3)\n",
"observables = [1,3,2]\n",
"\n",
"# The expectation value <psi2|X_0.id_1.Z_2.Y_3|psi2> is obtained via:\n",
"average = psi2.ExpectationValue(qubits_to_be_measured, observables, 1.);\n",
"print(\"Expectation value <+-01|X_0.id_1.Z_2.Y_3|+-01> = {}\\n\".format(average));\n",
"\n",
"# The expectation value <psi2|X_0.id_1.Z_2.Y_3|psi2> is obtained via:\n",
"qubits_to_be_measured = [0,2,3]\n",
"observables = [1,3,3]\n",
"average = psi2.ExpectationValue(qubits_to_be_measured, observables, 1.);\n",
"print(\"Expectation value <+-01|X_0.id_1.Z_2.Z_3|+-01> = {}\\n\".format(average));\n",
"\n",
"# Trivial expectation:\n",
"average = psi2.ExpectationValue([0],[1], 1.);\n",
"print(\"Expectation value <+-01|X_0|+-01> = {}\\n\".format(average));\n",
"\n",
"# The expectation value <psi2|X_0.id_1.id_2.Z_3|psi2> is obtained via:\n",
"average = psi2.ExpectationValue([0,3],[1,3], 1.);\n",
"print(\"Expectation value <+-01|X_0.Z_3|+-01> = {}\\n\".format(average));"
]
},
{
"cell_type": "code",
"execution_count": 13,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Probability that qubit 0, if measured, is in state |1> = 0.0\n",
"\n",
"Probability that qubit 1, if measured, is in state |1> = 1.0\n",
"\n",
"Probability that qubit 2, if measured, is in state |1> = 0.0\n",
"\n",
"Probability that qubit 3, if measured, is in state |1> = 1.0\n",
"\n",
"Expectation value <+-01|X_0.id_1.Z_2.Y_3|+-01> = 0.0\n",
"\n",
"Expectation value <+-01|X_0.id_1.Z_2.Z_3|+-01> = -0.9999999999999989\n",
"\n"
]
}
],
"source": [
"# Prepare the state |+-01>\n",
"index = 2+8;\n",
"psi2.Initialize(\"base\",index);\n",
"# Notice that GetProbability() does not change the state.\n",
"for qubit in range(0,num_qubits):\n",
" prob = psi2.GetProbability( qubit );\n",
" print(\"Probability that qubit {}, if measured, is in state |1> = {}\\n\".format(qubit, prob));\n",
"\n",
"psi2.ApplyHadamard(0);\n",
"psi2.ApplyHadamard(1);\n",
"\n",
"# The Pauli string given by: X_0 . id_1 . Z_2 . Y_3\n",
"# Such observable is defined by the position of the non-trivial Pauli matrices:\n",
"qubits_to_be_measured = [0,2,3]\n",
"\n",
"# And by the corresponding Pauli matrices (X=1, Y=2, Z=3)\n",
"observables = [1,3,2]\n",
"\n",
"# The expectation value <psi2|X_0.id_1.Z_2.Y_3|psi2> is obtained via:\n",
"average = psi2.ExpectationValue(qubits_to_be_measured, observables, 1.);\n",
"print(\"Expectation value <+-01|X_0.id_1.Z_2.Y_3|+-01> = {}\\n\".format(average));\n",
"\n",
"# The expectation value <psi2|X_0.id_1.Z_2.Y_3|psi2> is obtained via:\n",
"qubits_to_be_measured = [0,2,3]\n",
"observables = [1,3,3]\n",
"average = psi2.ExpectationValue(qubits_to_be_measured, observables, 1.);\n",
"print(\"Expectation value <+-01|X_0.id_1.Z_2.Z_3|+-01> = {}\\n\".format(average));"
]
},
{
"cell_type": "code",
"execution_count": 14,
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Expectation value <+-01|X_0|+-01> = 1.0\n",
"\n",
"Expectation value <+-01|X_0.Z_3|+-01> = -1.0000000000000002\n",
"\n",
"Expectation value <+-01|X_0.Z_2|+-01> = 0.999999999999998\n",
"\n",
"Expectation value <+-01|X_1.Z_2|+-01> = -1.0000000000000002\n",
"\n"
]
}
],
"source": [
"# Extra expectation values.\n",
"\n",
"# Prepare the state |+-01>\n",
"index = 2+8;\n",
"psi2.Initialize(\"base\",index);\n",
"psi2.ApplyHadamard(0);\n",
"psi2.ApplyHadamard(1);\n",
"\n",
"# The expectation value of X_0:\n",
"average = psi2.ExpectationValue([0],[1], 1.);\n",
"print(\"Expectation value <+-01|X_0|+-01> = {}\\n\".format(average));\n",
"\n",
"# The expectation value of X_0.Z_3:\n",
"average = psi2.ExpectationValue([0,3],[1,3], 1.);\n",
"print(\"Expectation value <+-01|X_0.Z_3|+-01> = {}\\n\".format(average));\n",
"\n",
"# The expectation value of X_0.Z_2:\n",
"average = psi2.ExpectationValue([0,2],[1,3], 1.);\n",
"print(\"Expectation value <+-01|X_0.Z_2|+-01> = {}\\n\".format(average));\n",
"\n",
"# The expectation value of X_1.Z_2:\n",
"average = psi2.ExpectationValue([1,2],[1,3], 1.);\n",
"print(\"Expectation value <+-01|X_1.Z_2|+-01> = {}\\n\".format(average));"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"----\n",
"### END\n",
"----"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
}
},
"nbformat": 4,
"nbformat_minor": 2
}

View File

@ -0,0 +1,201 @@
![C++ build with CMake](https://github.com/iqusoft/intel-qs/workflows/C++%20build%20with%20CMake/badge.svg)
![Python build (no MPI)](https://github.com/iqusoft/intel-qs/workflows/Python%20build%20(no%20MPI)/badge.svg)
[![arXiv](https://img.shields.io/static/v1?label=arXiv&message=2001.10554&color=success)](https://arxiv.org/abs/2001.10554)
[![arXiv](https://img.shields.io/static/v1?label=arXiv&message=1601.07195&color=inactive)](https://arxiv.org/abs/1601.07195)
# Intel Quantum Simulator
Intel Quantum Simulator (Intel-QS), also known as qHiPSTER (The Quantum High Performance Software Testing Environment),
is a simulator of quantum circuits optimized to take maximum advantage of multi-core and multi-nodes architectures.
It is based on a complete representation of the qubit state, but avoids the explicit representation of gates and
other quantum operations in terms of matrices.
Intel-QS uses MPI (message-passing-interface) protocols to handle the communication between distributed
resources that are used to store and manipulate the quantum state.
----
## Build instructions
Intel-QS builds as a shared library which, once linked to the application program, allows to take advantage
of the high-performance implementation of circuit simulations.
The library can be built on a variety of different systems, from laptop to HPC server systems.
The directory structure of the repository can be found in
[intel-qs/docs/directory_structure.md](/docs/directory_structure.md).
The library object is: `/builb/lib/libiqs.so`
### Requirements
The following packages are required by the installation:
* CMake tools version 3.12+
* MPICH3 library for enabling the distributed communication
* optional: MKL for distributed random number generation
* optional: PyBind11 (installed via conda, not pip) required by the Python bunding of Intel-QS
The first step is cloning the repository:
```bash
git clone https://github.com/iqusoft/intel-qs.git
cd intel-qs
```
### Use Intel Parallel Studio compilers to build Intel-QS
If you wish to build Intel-QS using the latest Intel compiler technologies, then
you need to configure your environment properly according to that tool's documentation.
Assuming that you have installed Intel Parallel Studio in the standard location on your
system, you should invoke the following scripts through the source command on Linux.
```bash
source /opt/intel/bin/compilervars.sh -arch intel64 -platform linux
source /opt/intel/compiler_and_libraries/linux/mpi/intel64/bin/mpivars.sh
```
Now, use CMake to generate the appropriate makefiles to use the Intel Parallel Studio compilers.
The installation follows the out-of-source building and requires the creation of the directory `build`.
This directory is used to collect all the files generated during the installation process.
```bash
mkdir build
cd build
CXX=mpiicpc cmake -DIqsMPI=ON -DIqsUtest=ON ..
make
```
By default, MKL is required when Intel compilers are used.
To re-build Intel-QS with different settings or options, we recommend to delete all content of the
`build` directory and then restart from the CMake command.
### Use standard GNU tools to build Intel-QS
If you wish to build Intel-QS using only standard GNU compilers type:
```bash
mkdir build
cd build
CXX=g++ cmake -DIqsMPI=OFF ..
make
```
By default, MKL is not required when GNU compilers are used.
Optionally, MPI can be included by setting the option `-DIqsMPI=ON` instead. You must ensure
that you have at least version 3.1 of MPICH installed for the build to succeed.
https://www.mpich.org
### Enable MPI protocol for distributed memory use
The above installation enables MPI functionalities to deploy Intel-QS on High Performance
Computing and Cloud Computing infrastructures. There is the option of disabling MPI:
simply set the CMake option selection to `-DIqsMPI=OFF`
(or just omit the option selection since MPI is disabled by default in the CMake build).
### Enable Latest Vector Capability
To compile with the latest instruction set supported by your architecture, there is the option `-DIqsNative`.
Compiled with `-DIqsNative=ON`, the latest vector instructions available on your machine, e.g. AVX2, AVX512, are used.
By default, `-DIqsNative=OFF`.
If the machine you compile and the machine you run have different vector capabilities, turning on `IqsNative=ON` might cause run-time problems.
Underneath, this option uses [`-xhost`](https://software.intel.com/en-us/cpp-compiler-developer-guide-and-reference-xhost-qxhost)
with Intel compilers and [`-march=native`](https://gcc.gnu.org/onlinedocs/gcc/x86-Options.html) with GNU compilers.
### Enable Python binding (only available without MPI)
By default, whenever MPI is disabled, the building process includes the Python binding for
Intel-QS. The binding code uses the Pybind11 library which needs to be installed via 'conda'
(and not simply with pip) to include the relevant information in CMake.
See [this page](https://github.com/pybind/pybind11/issues/1628) for more info on this issue.
To disable the Python wrap, even without MPI, set the CMake option selection to
`-DIqsPython=OFF`.
### Unit test
By default, with MPI either enabled or disabled, the building process includes a suite
of unit tests written in the [googletest framework](https://github.com/google/googletest).
Following the recommended integration, the CMake building process automatically downloads
the up-to-date repository of gtest and installs it in the `build` path.
To disable the unit tests, set the CMake option selection to `-DIqsUtest=OFF`.
To run the unit tests, from `/build` launch the executable `./bin/utest`.
### Recommended build for HPC.
The recommended building process requires
[Intel Math Kernel Library](https://software.intel.com/en-us/mkl)
and the [MPI-ICPC compiler](https://software.intel.com/en-us/node/528770).
When the program is run in hybrid configuration (OpenMP+MPI), we recommend to manage
the OpenMP affinity directly. Affinity settings can be set using the syntax:
`KMP_AFFINITY=compact,1,0,granularity=fine`.
A quick look at the options can be found at
[this page](https://www.nas.nasa.gov/hecc/support/kb/using-intel-openmp-thread-affinity-for-pinning_285.html).
----
## Docker: build image and run/execute container
`Dockerfile` includes the instructions to build the docker image of an Ubuntu machine
with Intel-QS already installed. The image can be 'run' to create a container.
The container can be 'executed' to login into the machine.
```bash
docker build -t qhipster .
docker run -d -t qhipster
docker ps
docker exec -itd <container_id> /bin/bash
```
If Docker is used on a Windows host machine, the last line should be substituted by:
`winpty docker exec -itd <container_id> //bin/bash`.
----
## Getting started with Intel-QS
The simplest way of familiarize with the Intel Quantum Simulator is by exploring
the tutorials provided in the directory `tutorials/`.
In particular, the code `tutorials/get_started_with_IQS.cpp` provides step-by-step
description of the main commands to:
define a qubit register object, perform quantum gates, measure one or multiple qubits.
If the Python bindings were enabled, the same learning can be performed using the iPython
notebook `tutorials/get_started_with_IQS.ipynb`.
----
## How to contribute
Thanks for your interest in the project! We welcome pull requests from developers
of all skill levels. If you would like to contribute to Intel-QS, please take a
look to our [contributing policy](CONTRIBUTING.md) and also to the
[code of conduct](CODE_OF_CONDUCT.md).
For any bug, we use GitHub issues [GitHub issues](https://github.com/iqusoft/intel-qs/issues). Please submit your request there.
----
## How to contact us
If you have a question or want to discuss something, feel free to send an email to
[Justin Hogaboam](justin.w.hogaboam@intel.com),
[Gian Giacomo Guerreschi](gian.giacomo.guerreschi@intel.com), or to
[Fabio Baruffa](fabio.baruffa@intel.com).
----
## How to cite
When using Intel Quantum Simulator for research projects, please cite:
Gian Giacomo Guerreschi, Justin Hogaboam, Fabio Baruffa, Nicolas P. D. Sawaya
*Intel Quantum Simulator: A cloud-ready high-performance simulator of quantum circuits*
[arXiv:2001.10554](https://arxiv.org/abs/2001.10554)
The original implementation is described here:
Mikhail Smelyanskiy, Nicolas P. D. Sawaya, Alán Aspuru-Guzik
*qHiPSTER: The Quantum High Performance Software Testing Environment*
[arXiv:1601.07195](https://arxiv.org/abs/1601.07195)

39
docs/source/index.rst Normal file
View File

@ -0,0 +1,39 @@
.. Intel QS documentation master file, created by
sphinx-quickstart on Tue Oct 27 20:11:28 2020.
You can adapt this file completely to your liking, but it should at least
contain the root `toctree` directive.
Welcome to Intel QS's documentation!
====================================
.. toctree::
:maxdepth: 2
getting-started
.. toctree::
:maxdepth: 2
:caption: Tutorials:
get_started_examples
qaoa_example
.. toctree::
:maxdepth: 2
:caption: Libraries:
CONTRIBUTING
.. toctree::
:maxdepth: 2
api/library_root
Indices and tables
==================
* :ref:`genindex`
* :ref:`modindex`
* :ref:`search`

File diff suppressed because one or more lines are too long

View File

@ -4,7 +4,7 @@ import sys
sys.path.insert(0, "../build/lib/")
import intelqs_py as iqs
iqs.init()
iqs.EnvInit()
rank = iqs.MPIEnvironment.GetRank()
print("Creation of a 2-qubit state at rank {}",format(rank));
@ -13,4 +13,4 @@ psi = iqs.QubitRegister(2, "base", 0, 0);
print("The IQS library was successfully imported and initialized.")
iqs.finalize()
iqs.EnvFinalize()