Qiskit Machine Learning v0.5 移行ガイド#
このチュートリアルでは、コードを Qiskit Machine Learning v0.4 から v0.5 へマイグレーションするプロセスをガイドします。
はじめに#
Qiskit Machine Learning のリリース0.5における主な焦点は、Qiskitで導入されたPrimitiveへの量子カーネルや量子ニューラルネットワークなどのベースの計算ブロックの移行と、アルゴリズムにおけるprimitiveの拡張サポートです。
目次:
Primitiveの概要
新量子カーネル
新量子ニューラル・ネットワーク
その他の注意すべき非推奨事項
Primitiveの概要#
量子コンピューターが古典コンピューターと異なる点は、出力に非古典的な確率分布を生成することができる点です。確率分布の基本的な操作は、確率分布からのサンプリングと確率分布に基づく量の推定です。このサンプリングと推定という操作が、量子アルゴリズム開発の基本的な構成要素となっています。そのため、 `こちら <https://research.ibm.com/blog/qiskit-runtime-for-useful-quantum-computing>`_で発表したように,この2つの操作を実装したSamplerとEstimatorという基本プリミティブが導入されました。
Samplerクラスは、量子回路のビット列の確率または準確率を計算します。基本クラスは qiskit.primitives.BaseSampler です。
Estimatorクラスは、量子回路や観測値の期待値を推定するクラスです。基本クラスは qiskit.primitives.BaseEstimator です。
Qiskit Terraはコアインターフェースと2つの実装を提供します:
状態ベクトルベースのリファレンス実装です。この実装はバックエンドやシミュレーターを必要とせず、 quantum_info パッケージのクラスに依存しています。
バックエンドベースのprimitiveは、primitiveを直接サポートしないプロバイダー/バックエンドをサポートするためのものです。この実装では、primitiveに渡すバックエンドのインスタンスが必要です。
Qiskit Terra primitiveに関するより詳しい情報は documentation に記載されています。
他の実装についても触れておくとよいでしょう:
Aer primitiveは、Aerシミュレーターで使用されるものです。これらはTerraの対応するインターフェースを拡張したもので、Terraのprimitiveと同じように使用することができます。詳しくは documentation を参照してください。
IBMのデバイスで使用するためのRumtive primitiveです。実際のハードウェアでのクラウドコンピューティングに特化した実装です。`こちら __<https://qiskit.org/documentation/partners/qiskit_ibm_runtime/apidocs/runtime_service.html>``__を参照してください。
Terraはprimitiveとともに、QMLで非常に有用なprimitive的アルゴリズムを持っており、0.5の新機能で使用されています。
量子回路の勾配を計算するためのアルゴリズム。各コアprimitiveに対応する基本インターフェースがあり、量子回路の勾配を定義しています。勾配に関するドキュメントは `こちら <https://qiskit.org/documentation/stubs/qiskit.algorithms.gradients.html>`__です。
量子状態のペアの忠実度(近さ)を計算するアルゴリズム。現在、1つの実装のみが利用可能で、sampler primitiveを必要とし、compute-uncomputeメソッドに基づくものです。ドキュメントは `こちら <https://qiskit.org/documentation/stubs/qiskit.algorithms.state_fidelities.html>`__です。
この2つのアルゴリズムは、コアprimitiveと非常によく似ており、同じメソッドシグネチャーを共有しているため、primitiveパッケージに含まれていないにもかかわらず、高レベルのprimitiveとして呼び出すことができます。
新量子カーネル#
以前の実装では、1つのクラス QuantumKernel がすべてを担っていました。
回路の構築
回路の実行と回路間の重なりの評価
学習用パラメーターを提供
パラメーターに割り当てられた値の追跡
この実装は高度で柔軟性に欠け、新しいprimitiveのサポートを追加するのは困難でした。そこで、柔軟かつ拡張可能な新しい量子カーネルを開発しました。新しい設計の目標は以下の通りです。
Primitiveに移行し、Fidelity アルゴリズムを活用します。これにより、ユーザーは独自のFidelity 計算の実装をプラグインすることができます。
訓練可能な機能を専用のクラスに抽出する。
他のカーネルが拡張可能な基本クラスを導入する。
量子カーネルの新しい設計を次の図に示します。
新しいカーネルは、 quantum_instance
パラメーターを除いて、同じインターフェースと同じパラメーターを公開しています。このパラメーターは直接的に置き換えることができず、代わりにfidelityパラメーターを使用しなければなりません。バックエンドの処理・選択は、以前は``quantum_instance``を使用していましたが、現在は fidelity
に与えられたSampler primitiveを介して処理されます。
図に示すような新しい階層が導入されます。
ベースとなる抽象クラス BaseKernel が導入されました。すべての具体的な実装は、このクラスを継承する必要があります。
Fidelity ベースの量子カーネル FidelityQuantumKernel が追加されました。これは、以前の量子カーネル実装をそのまま置き換えたものです。新しいクラスは、オーバーラップを推定し、カーネル行列を構築するために、Fidelity(忠実度)のインスタンスを取るという違いがあります。
また、量子カーネルを学習するための抽象クラス TrainableKernel が追加されました.
Fidelity ベースの量子カーネル TrainableFidelityQuantumKernel が導入されました.これは、従来の量子カーネルを 置き換える もので、訓練可能なカーネルが必要な場合に使用します。トレーナである QuantumKernelTrainer は,新型と旧型の両方の量子カーネルを受け入れることができるようになりました。
以前の量子カーネル実装である`QuantumKernel <https://qiskit.org/documentation/machine-learning/stubs/qiskit_machine_learning.kernels.QuantumKernel.html>`__ は,新しい抽象クラスを継承しており,新しく導入されたインターフェースと互換性を持っています.この実装は 現在 非推奨 であり,将来のリリースで非推奨となり,その後削除される予定です。新しいプリミティブベースの量子カーネルを使用する必要があります。
QSVC、QSVR、その他のカーネルベースのアルゴリズムは更新され、両方の実装で動作するようになります。
例えば,QSVM分類器は以下のように学習させることができます。
データセットの準備#
ランダム性を固定します。
from qiskit.utils import algorithm_globals
algorithm_globals.random_seed = 123456
Scikit-learn を使用して簡単なデータセットを生成します。
from sklearn.datasets import make_blobs
features, labels = make_blobs(
n_samples=20,
centers=2,
center_box=(-1, 1),
cluster_std=0.1,
random_state=algorithm_globals.random_seed,
)
量子カーネルの以前の実装#
前回の実装では、 QuantumInstance
のインスタンスを作成するところから始めました。このクラスは、量子回路が実行される場所を定義します。今回は、量子インスタンスに状態ベクトルシミュレーターをラップしています。
from qiskit import BasicAer
from qiskit.utils import QuantumInstance
sv_qi = QuantumInstance(
BasicAer.get_backend("statevector_simulator"),
seed_simulator=algorithm_globals.random_seed,
seed_transpiler=algorithm_globals.random_seed,
)
その後、量子カーネルを作ります。
from qiskit.circuit.library import ZZFeatureMap
from qiskit_machine_learning.kernels import QuantumKernel
feature_map = ZZFeatureMap(2)
previous_kernel = QuantumKernel(feature_map=feature_map, quantum_instance=sv_qi)
そして最終的にはSVM分類器に適合します。
from qiskit_machine_learning.algorithms import QSVC
qsvc = QSVC(quantum_kernel=previous_kernel)
qsvc.fit(features, labels)
qsvc.score(features, labels)
0.95
新しい量子カーネル実装#
新しい実装では、Fidelityのインスタンスを作成するところから始めます。Fidelityはオプションで、何も渡されない場合は量子カーネルが自動的に作成します。しかし、ここでは、説明のために手動で作成します。Fidelityのインスタンスを作成するために、Samplerを渡します。Samplerとは、量子回路を実行する際に参照する実装のことであり、量子回路が実行される場所を定義します。QiskitのRuntime serviceを活用するために、QiskitRuntimeService <https://qiskit.org/documentation/partners/qiskit_ibm_runtime/stubs/qiskit_ibm_runtime.QiskitRuntimeService.html> からSampler インスタンスを作成することができます。
from qiskit.algorithms.state_fidelities import ComputeUncompute
from qiskit.primitives import Sampler
fidelity = ComputeUncompute(sampler=Sampler())
次に、fidelify (忠実度) インスタンスで新しい量子カーネルを作成します。
from qiskit_machine_learning.kernels import FidelityQuantumKernel
feature_map = ZZFeatureMap(2)
new_kernel = FidelityQuantumKernel(feature_map=feature_map, fidelity=fidelity)
そして、前と同じようにSVM分類器を当てはめます。
from qiskit_machine_learning.algorithms import QSVC
qsvc = QSVC(quantum_kernel=new_kernel)
qsvc.fit(features, labels)
qsvc.score(features, labels)
0.95
新量子ニューラル・ネットワーク#
量子ニューラルネットワークの変更は、量子カーネルほど劇的なものではありません。また、既存のニューラルネットワークを置き換えるものとして、2つの新しいネットワークが導入されています。 SamplerQNN と EstimatorQNN で、既存の CircuitQNN 、 OpflowQNN 、 TwoLayerQNN を置き換えるもので、詳細は以下の通りです。
SamplerQNN#
新しい Sampler Quantum Neural Network は、sampler primitive、sampler Gradientsを活用し、 CircuitQNN を 直接置き換える ものです。
新しい SamplerQNN は既存の CircuitQNN と同様のインターフェイスを公開しますが、いくつかの違いがあります。1つは quantum_instance
パラメーターです。このパラメーターは直接の置き換えがなく、代わりに sampler
パラメーターを使用する必要があります。 gradient
パラメーターは CircuitQNN の実装と同じ名前を保っていますが、入力としてOpflow gradientクラスを受け付けなくなりました。代わりに、このパラメーターは(オプションでカスタム)primitive gradientを期待します。 sampling
option は、現在samplerが公開していない情報であり、将来の低レベルprimitiveに対応する可能性があるため、当面の間、削除されました。
CircuitQNN をベースとした VQC のような既存の学習アルゴリズムは、両方の実装を受け入れるように更新されました。 NeuralNetworkClassifier の実装は変更されていません。
既存の CircuitQNN は、現在 保留中の非推奨 となっており、将来のリリースで非推奨となり、その後削除される予定です。
ここでは、両ネットワークを用いた変分量子分類器の学習方法を紹介します。この目的のために、量子カーネルのために生成されたデータセットを再利用します。両者の量子ニューラルネットワークでは、特徴量マップ、ansatzを構築し、それらを1つの量子回路に結合する必要があります。
from qiskit import QuantumCircuit
from qiskit.circuit.library import RealAmplitudes
num_inputs = 2
feature_map = ZZFeatureMap(num_inputs)
ansatz = RealAmplitudes(num_inputs, reps=1)
circuit = QuantumCircuit(num_inputs)
circuit.compose(feature_map, inplace=True)
circuit.compose(ansatz, inplace=True)
同様に、解釈関数も必要です。ここでは、ビット列を:math:0 または \(1\) にマップする、通常のパリティ関数を定義します。
def parity(x):
return "{:b}".format(x).count("1") % 2
両方のネットワークから同じ結果が得られるように、初期点を固定します。
initial_point = algorithm_globals.random.random(ansatz.num_parameters)
CircuitQNN
を用いた分類器の構築#
CircuitQNN
のインスタンスを作成し、量子カーネル用に作成した量子インスタンスを再利用します。
from qiskit_machine_learning.neural_networks import CircuitQNN
circuit_qnn = CircuitQNN(
circuit=circuit,
input_params=feature_map.parameters,
weight_params=ansatz.parameters,
interpret=parity,
output_shape=2,
quantum_instance=sv_qi,
)
ネットワークから分類器を構築し、それを訓練し、スコアをつけます。良い結果を目指しているわけではないので、全体の実行時間を短縮するために、反復回数は少なめに設定されています。
from qiskit.algorithms.optimizers import COBYLA
from qiskit_machine_learning.algorithms import NeuralNetworkClassifier
classifier = NeuralNetworkClassifier(
neural_network=circuit_qnn,
loss="cross_entropy",
one_hot=True,
optimizer=COBYLA(maxiter=40),
initial_point=initial_point,
)
classifier.fit(features, labels)
classifier.score(features, labels)
0.6
SamplerQNN
を用いた分類器の構築#
QuantumInstance
の代わりに参照元 Sampler
のインスタンスを作成します。
from qiskit.primitives import Sampler
sampler = Sampler()
ここで、 SamplerQNN
のインスタンスを作成します。 CircuitQNN
との違いは、量子インスタンスではなく、samplerを渡すことです。
from qiskit_machine_learning.neural_networks import SamplerQNN
sampler_qnn = SamplerQNN(
circuit=circuit,
input_params=feature_map.parameters,
weight_params=ansatz.parameters,
interpret=parity,
output_shape=2,
sampler=sampler,
)
通常通り分類器を構築し、フィットさせます。 neural_network
として、作成した SamplerQNN
を渡していますが、これだけの違いです。
classifier = NeuralNetworkClassifier(
neural_network=sampler_qnn,
loss="cross_entropy",
one_hot=True,
optimizer=COBYLA(maxiter=40),
initial_point=initial_point,
)
classifier.fit(features, labels)
classifier.score(features, labels)
0.6
量子ニューラルネットワークを手動で構築する代わりに、 VQC
をトレーニングすることができます。 VQC
は、量子インスタンスとsamplerを受け取り、渡された内容に応じて、CircuitQNN
と SamplerQNN
をそれぞれ自動的に構築します。
EstimatorQNN#
新しい Estimator quantum neural network は、Estimator primitive、Estimator gradientsを活用し、 OpflowQNN を **直接置き換える ** ものです。
新しい EstimatorQNN は、既存の OpflowQNN と同様のインターフェースを公開しますが、いくつかの相違点があります。1つは quantum_instance
パラメーターです。このパラメーターには直接的な代替がなく、代わりに estimator
パラメーターを使用する必要があります。 gradient
パラメーターは OpflowQNN の実装と同じ名前を持ちますが、入力としてOpflow gradientクラスを受け付けなくなりました。代わりに、このパラメーターは(オプションでカスタム)primitive gradientを期待するものです。
VQR のような TwoLayerQNN に基づく既存の学習アルゴリズムは、両方の実装を受け入れるように更新されます。 NeuralNetworkRegressor の実装は変更されていません。
既存の OpflowQNN は、現在 保留中の非推奨 となっており、将来のリリースで非推奨となり、その後削除される予定です。
両方のネットワークを用いた変分量子回帰の学習方法を紹介します。まず、単純な回帰データセットを生成するところから始めます。
import numpy as np
num_samples = 20
eps = 0.2
lb, ub = -np.pi, np.pi
features = (ub - lb) * np.random.rand(num_samples, 1) + lb
labels = np.sin(features[:, 0]) + eps * (2 * np.random.rand(num_samples) - 1)
まだ、量子ニューラルネットワークともに、特徴量マップ、ansatzを構築し、それらを組み合わせて一つの量子回路にする必要があります。
from qiskit.circuit import Parameter
num_inputs = 1
feature_map = QuantumCircuit(1)
feature_map.ry(Parameter("input"), 0)
ansatz = QuantumCircuit(1)
ansatz.ry(Parameter("weight"), 0)
circuit = QuantumCircuit(num_inputs)
circuit.compose(feature_map, inplace=True)
circuit.compose(ansatz, inplace=True)
両方のネットワークから同じ結果が得られるように、初期点を固定します。
initial_point = algorithm_globals.random.random(ansatz.num_parameters)
OpflowQNN
を用いた回帰器の構築#
OpflowQNN
のインスタンスを作成し、量子カーネル用に作成した量子インスタンスを再利用します。
from qiskit.opflow import PauliSumOp, StateFn
from qiskit_machine_learning.neural_networks import OpflowQNN
observable = PauliSumOp.from_list([("Z", 1)])
operator = StateFn(observable, is_measurement=True) @ StateFn(circuit)
opflow_qnn = OpflowQNN(
operator=operator,
input_params=feature_map.parameters,
weight_params=ansatz.parameters,
quantum_instance=sv_qi,
)
ネットワークから回帰器を構築し、それを訓練し、スコアをつけます。この場合、勾配ベースのオプティマイザーを使用するため、ネットワークは勾配の枠組みを利用し、データセットの性質上、非常に早く収束します。
from qiskit.algorithms.optimizers import L_BFGS_B
from qiskit_machine_learning.algorithms import NeuralNetworkRegressor
regressor = NeuralNetworkRegressor(
neural_network=opflow_qnn,
optimizer=L_BFGS_B(maxiter=5),
initial_point=initial_point,
)
regressor.fit(features, labels)
regressor.score(features, labels)
0.9681198723451012
EstimatorQNN
を用いた回帰器の構築#
リファレンスであるEstimatorのインスタンスを作成します。Qiskitのruntimeサービスを活用するため、`QiskitRuntimeService <https://qiskit.org/documentation/partners/qiskit_ibm_runtime/stubs/qiskit_ibm_runtime.QiskitRuntimeService.html>`__からEstimatorのインスタンスを作成することもできます。
from qiskit.primitives import Estimator
estimator = Estimator()
ここで、EstimatorQNN
のインスタンスを作成する。このネットワークは \(Z^{\otimes n}\) という観測量をします。ここで \(n\) は量子ビットの数です。
from qiskit_machine_learning.neural_networks import EstimatorQNN
estimator_qnn = EstimatorQNN(
circuit=circuit,
input_params=feature_map.parameters,
weight_params=ansatz.parameters,
estimator=estimator,
)
変量量子回帰器を構築し、それをフィッティングします。この場合、勾配ベースのオプティマイザーを使用するため、ネットワークは自動的に作成される default estimator gradient を使用します。
from qiskit.algorithms.optimizers import L_BFGS_B
from qiskit_machine_learning.algorithms import VQR
regressor = NeuralNetworkRegressor(
neural_network=estimator_qnn,
optimizer=L_BFGS_B(maxiter=5),
initial_point=initial_point,
)
regressor.fit(features, labels)
regressor.score(features, labels)
0.9681198723451012
量子ニューラルネットワークを手動で構築する代わりに、 VQR
をトレーニングすることができます。 VQR
は、量子インスタンスとestimatorを受け取り、渡された内容に応じて、 TwoLayerQNN
と EstimatorQNN
をそれぞれ自動的に構築します。
その他の注意すべき非推奨事項#
上記で明確に言及されていない他のいくつかのコンポーネントも、非推奨または非推奨保留となっています:
TwoLayerQNN は非推奨です。ユーザーは代わりにEstimatorQNN <https://qiskit.org/documentation/machine-learning/stubs/qiskit_machine_learning.neural_networks.EstimatorQNN.html>`__ を使うべきです。
Distribution Learners パッケージは完全に非推奨です.このパッケージは DiscriminativeNetwork, GenerativeNetwork, NumPyDiscriminator, PyTorchDiscriminator, QuantumGenerator, QGAN などのクラスが含まれています。代わりに、`新しいQGANチュートリアル <../tutorials/04_torch_qgan.ipynb>`__を参照してください。このチュートリアルでは、量子ニューラルネットワークを用いたPyTorchベースのQGANの構築方法をステップバイステップで紹介しています。
Runtimeパッケージは非推奨です。このパッケージには、アルゴリズムインターフェイスにQiskit Runtimeを組み込み、クラウドでのアルゴリズムやスクリプトの使用を容易にするQiskit Programsへのクライアントが含まれています。Primitiveやruntimeを活用するには、QiskitRuntimeService を使用する必要があります。
import qiskit.tools.jupyter
%qiskit_version_table
%qiskit_copyright
Version Information
Qiskit Software | Version |
---|---|
qiskit-terra | 0.25.0 |
qiskit-aer | 0.13.0 |
qiskit-machine-learning | 0.7.0 |
System information | |
Python version | 3.8.13 |
Python compiler | Clang 12.0.0 |
Python build | default, Oct 19 2022 17:54:22 |
OS | Darwin |
CPUs | 10 |
Memory (Gb) | 64.0 |
Thu Sep 14 13:57:31 2023 IST |
This code is a part of Qiskit
© Copyright IBM 2017, 2023.
This code is licensed under the Apache License, Version 2.0. You may
obtain a copy of this license in the LICENSE.txt file in the root directory
of this source tree or at http://www.apache.org/licenses/LICENSE-2.0.
Any modifications or derivative works of this code must retain this
copyright notice, and modified files need to carry a notice indicating
that they have been altered from the originals.