Qiskit C APIのインストール
このガイドでは、Qiskit C APIのインストール方法と使用方法について説明します。CでQiskitのPythonワークフローを拡張する方法については、Qiskit C APIでPythonを拡張するをご覧ください。
以下の例では、CでObservableを構築します:
// file: example.c
#include <stdio.h>
#include <stdint.h>
#include <qiskit.h>
int main(int argc, char *argv[]) {
// build a 100-qubit empty observable
uint32_t num_qubits = 100;
QkObs *obs = qk_obs_zero(num_qubits);
// add the term 2 * (X0 Y1 Z2) to the observable
QkComplex64 coeff = {2, 0};
QkBitTerm bit_terms[3] = {QkBitTerm_X, QkBitTerm_Y, QkBitTerm_Z}; // bit terms: X Y Z
uint32_t indices[3] = {0, 1, 2}; // indices: 0 1 2
QkObsTerm term = {coeff, 3, bit_terms, indices, num_qubits};
qk_obs_add_term(obs, &term); // append the term
// print some properties and the observable itself
printf("num_qubits: %i\n", qk_obs_num_qubits(obs));
printf("num_terms: %lu\n", qk_obs_num_terms(obs));
printf("observable: %s\n", qk_obs_str(obs));
// free the memory allocated for the observable
qk_obs_free(obs);
return 0;
}
UNIX系
このセクションでは、UNIX系システム向けのビルド手順を説明します。
必要条件
コンパイルには以下のツールが必要です:
- Rustコンパイラ:例としてQiskitをソースからインストールするガイドを参照してください
- Cコンパイラ:例えば、LinuxではGCC、MacOSではClangを使用します。QiskitのC APIはC11標準に準拠したコンパイラと互換性があります。
cbindgen:CヘッダーファイルをするためのツールでCするには、cargo install cbindgenでインストールできます。 コマンドラインからツールを実行できるようにする必要があります。/path/to/.cargo/binを含むようにPATH変数をエクスポートする必要がある場合があります。- Pythonライブラリのインストール(Python 3.9以上):動的リンク時にPythonライブラリが必要です。Pythonは実行時には使用されず、インタープリタは初期化されないことに注意してください。
libpythonからいくつかのシンボルが定義されている必要があるだけです。詳細についてはこちらのissueを参照してください。 - (GNU)Make:省略可能ですが、自動インストールプロセスに使用することを推奨します。
以下のコードですべてのインストールを確認できます:
rustc --version
gcc --version
cbindgen --version
make --version # optional, but recommended
ビルド
CヘッダーとライブラリをビルドするにはQiskitのルートディレクトリで以下のMakeコマンド1を実行します:
make c
これにより、コンパイル済みの共有ライブラリがdist/c/libに、すべての関数宣言を含むqiskit.hヘッダーがdist/c/includeに生成されます。正確なライブラリ名はプラットフォームによって異なります。例えば、UNIXではlibqiskit.so、MacOSではlibqiskit.dylibとなります。
(このステップでは現在多くの警告が出力されますが、これは想定内の動作であり、問題ではありません。将来のバージョンでは警告が削除される予定です。)
次に、Qiskit Cヘッダーとライブラリを使ってCプログラムをコンパイルできます:
gcc example.c -o example.o -I /path/to/dist/c/include -L /path/to/dist/c/lib -lqiskit
リンク時にQiskitライブラリが見つかるように、ランタイムライブラリパスに/path/to/dist/c/libを含めるよう設定してください。動的リンク時にPythonライブラリがデフォルトで利用できない場合は、これも追加する必要があります。これらのコマンドはプラットフォームによって異なります。Linuxの場合:
export LD_LIBRARY_PATH=/path/to/dist/c/lib:$LD_LIBRARY_PATH
# on Linux, the Python library is typically included in the dynamic library path per default
export LD_LIBRARY_PATH=/path/to/python/lib:$LD_LIBRARY_PATH
MacOSの場合:
export DYLD_LIBRARY_PATH=/path/to/dist/c/lib:$DYLD_LIBRARY_PATH
export DYLD_LIBRARY_PATH=/path/to/python/lib:$DYLD_LIBRARY_PATH
また、コンパイル時にコンパイラフラグに以下を追加することで、ランタイムライブラリパスを設定することもできます:
-Wl,-rpath,/path/to/dist/c/lib
# same for Python
さらに、動的リンク時にPythonライブラリが利用可能である必要があります。Linux環境ではこれが通常のデフォルト設定です。
バイナリを実行するには:
./example.o
上記のサンプルコードを使用している場合、以下のように出力されます:
num_qubits: 100
num_terms: 1
observable: SparseObservable { num_qubits: 100, coeffs: [Complex { re: 2.0, im: 0.0 }], bit_terms: [X, Y, Z], indices: [0, 1, 2], boundaries: [0, 3] }
Windows
このセクションでは、Windowsシステム向けのビルド手順を説明します。
必要条件
コンパイルには以下のツールが必要です:
- Rustコンパイラ:例としてQiskitをソースからインストールするガイドを参照してください
- Cコンパイラ:例えば、MSVCと
clコマンドを提供するネイティブコマンドプロンプト - Pythonのインストール。
python3.libとpython3.dllの両方へのアクセスが必要です cbindgen:CヘッダーファイルをするためのツールでCするには、cargo install cbindgenでインストールできます。 コマンドラインからツールを実行できるようにする必要があります。cargoのパスを含むようにPATH変数を更新する必要がある場合があります。
ビルド
まず、Qiskitのルートディレクトリで以下を実行してqiskit_cext動的ライブラリをコンパイルします:
set PATH="\path\to\pythonlib";%PATH%
cargo rustc --release --crate-type cdylib -p qiskit-cext
これにより、target/releaseに.dll動的ライブラリと関連する.dll.libファイルが生成されます。
次に、以下のコマンドでヘッダーを生成します:
cbindgen --crate qiskit-cext --output dist\c\include\qiskit.h
これにより、MSVC互換のヘッダーがdist\c\includeに書き込まれます。
次にclを使用してCプログラムをコンパイルできます。コンパイラがqiskitライブラリを見つけられるように、PATH変数にtarget\releaseを含めます。
set PATH="\path\to\target\release";%PATH%
cl example.c qiskit_cext.dll.lib -I\path\to\dist\c\include
実行前に、python3.dllへのパスを含める必要があります:
set PATH="\path\to\python3-dll";%PATH%
.\example.exe
実行すると以下のように出力されます:
num_qubits: 100
num_terms: 1
observable: SparseObservable { num_qubits: 100, coeffs: [Complex { re: 2.0, im: 0.0 }], bit_terms: [X, Y, Z], indices: [0, 1, 2], boundaries: [0, 3] }