Russian
Языки
English
Bengali
French
Hindi
Italian
Japanese
Korean
Malayalam
Russian
Spanish
Tamil
Turkish
Vietnamese
Shortcuts

Примечание

Страница создана на основе docs/tutorials/03_quantum_kernel.ipynb.

Квантовый ядерный метод машинного обучения

Общая задача машинного обучения заключается в поиске и изучении закономерностей в данных. Для многих наборов данных элементы данных (datapoints) лучше распознаются в большем пространстве измерений, через использование ядерной функции: \(k(\vec{x}_i, \vec{x}_j) = \langle f(\vec{x}_i), f(\vec{x}_j) \rangle\), где \(k\) - ядерная функция, \(\vec{x}_i, \vec{x}_j\) - входные данные с количеством измерений равным \(n\), \(f\) — это преобразование от \(n\)-мерного до \(m\)-мерного пространства и \(\langle a,b \rangle\) обозначает точечный результат. При рассмотрении конечных данных, ядерная функция может быть представлена в виде матрицы: \(K_{ij} = k(\vec{x}_i,\vec{x}_j)\).

В квантовом машинном обучении методом ядерной функции, преобразование \(\phi(\vec{x})\) используется для сопоставления классической векторной функции \(\vec{x} с квантовым Гильбертовым пространством, :math:\), таким, что \(K_{ij} = \left| \langle \phi^\dagger(\vec{x}_j)| \phi(\vec{x}_i) \rangle \right|^{2}\). См. Контролируемое обучение с квантово расширенными функциональными пространствами для более подробной информации.

В данном блокноте мы используем qiskit для вычисления ядерной матрицы с использованием квантовой функции преобразования, а затем используем эту матрицу в алгоритмах классификации и кластеризации scikit-learn.

[3]:
import matplotlib.pyplot as plt
import numpy as np

from sklearn.svm import SVC
from sklearn.cluster import SpectralClustering
from sklearn.metrics import normalized_mutual_info_score

from qiskit import BasicAer
from qiskit.circuit.library import ZZFeatureMap
from qiskit.utils import QuantumInstance, algorithm_globals
from qiskit_machine_learning.algorithms import QSVC
from qiskit_machine_learning.kernels import QuantumKernel
from qiskit_machine_learning.datasets import ad_hoc_data

seed = 12345
algorithm_globals.random_seed = seed

Классификация

Для нашего примера классификации мы будем использовать набор данных ad hoc dataset как в статье Supervised learning with quantum enhanced feature spaces <https://arxiv.org/pdf/1804.11326.pdf>`__, и алгоритм ``scikit-learn, поддерживающий алгоритм векторной машинной классификации (svc).

[2]:
adhoc_dimension = 2
train_features, train_labels, test_features, test_labels, adhoc_total = ad_hoc_data(
    training_size=20,
    test_size=5,
    n=adhoc_dimension,
    gap=0.3,
    plot_data=False,
    one_hot=False,
    include_sample_total=True,
)

plt.figure(figsize=(5, 5))
plt.ylim(0, 2 * np.pi)
plt.xlim(0, 2 * np.pi)
plt.imshow(
    np.asmatrix(adhoc_total).T,
    interpolation="nearest",
    origin="lower",
    cmap="RdBu",
    extent=[0, 2 * np.pi, 0, 2 * np.pi],
)

plt.scatter(
    train_features[np.where(train_labels[:] == 0), 0],
    train_features[np.where(train_labels[:] == 0), 1],
    marker="s",
    facecolors="w",
    edgecolors="b",
    label="A train",
)
plt.scatter(
    train_features[np.where(train_labels[:] == 1), 0],
    train_features[np.where(train_labels[:] == 1), 1],
    marker="o",
    facecolors="w",
    edgecolors="r",
    label="B train",
)
plt.scatter(
    test_features[np.where(test_labels[:] == 0), 0],
    test_features[np.where(test_labels[:] == 0), 1],
    marker="s",
    facecolors="b",
    edgecolors="w",
    label="A test",
)
plt.scatter(
    test_features[np.where(test_labels[:] == 1), 0],
    test_features[np.where(test_labels[:] == 1), 1],
    marker="o",
    facecolors="r",
    edgecolors="w",
    label="B test",
)

plt.legend(bbox_to_anchor=(1.05, 1), loc="upper left", borderaxespad=0.0)
plt.title("Ad hoc dataset for classification")

plt.show()
../_images/tutorials_03_quantum_kernel_3_0.png

С нашими готовыми наборами данных для обучения и тестирования, мы настроим класс QuantumKernel для вычисления с помощью ZFeatureMap, и BasicAer qasm_simulator используя 1024 вычисления.

[3]:
adhoc_feature_map = ZZFeatureMap(feature_dimension=adhoc_dimension, reps=2, entanglement="linear")

adhoc_backend = QuantumInstance(
    BasicAer.get_backend("qasm_simulator"), shots=1024, seed_simulator=seed, seed_transpiler=seed
)

adhoc_kernel = QuantumKernel(feature_map=adhoc_feature_map, quantum_instance=adhoc_backend)

Алгоритм scikit-learn svc позволяет нам определить пользовательское ядро двумя способами: путем предоставления ядра в качестве вызываемой функции или путем предварительного вычисления ядерной матрицы. Мы можем выполнить любую из двух операций, используя класс QuantumKernel в qiskit.

Следующий код предоставляет ядро в качестве вызываемой функции:

[4]:
adhoc_svc = SVC(kernel=adhoc_kernel.evaluate)
adhoc_svc.fit(train_features, train_labels)
adhoc_score = adhoc_svc.score(test_features, test_labels)

print(f"Callable kernel classification test score: {adhoc_score}")
Callable kernel classification test score: 1.0

Следующий код предварительно вычисляет и выводит в графическом виде данные об обучении и тестирует ядерные матрицы, прежде чем передать их алгоритму scikit-learn ``svc`:

[5]:
adhoc_matrix_train = adhoc_kernel.evaluate(x_vec=train_features)
adhoc_matrix_test = adhoc_kernel.evaluate(x_vec=test_features, y_vec=train_features)

fig, axs = plt.subplots(1, 2, figsize=(10, 5))
axs[0].imshow(
    np.asmatrix(adhoc_matrix_train), interpolation="nearest", origin="upper", cmap="Blues"
)
axs[0].set_title("Ad hoc training kernel matrix")
axs[1].imshow(np.asmatrix(adhoc_matrix_test), interpolation="nearest", origin="upper", cmap="Reds")
axs[1].set_title("Ad hoc testing kernel matrix")
plt.show()

adhoc_svc = SVC(kernel="precomputed")
adhoc_svc.fit(adhoc_matrix_train, train_labels)
adhoc_score = adhoc_svc.score(adhoc_matrix_test, test_labels)

print(f"Precomputed kernel classification test score: {adhoc_score}")
../_images/tutorials_03_quantum_kernel_9_0.png
Precomputed kernel classification test score: 1.0

qiskit также содержит класс qsvc, расширяющий класс sklearn svc, который может быть использован следующим образом:

[6]:
qsvc = QSVC(quantum_kernel=adhoc_kernel)
qsvc.fit(train_features, train_labels)
qsvc_score = qsvc.score(test_features, test_labels)

print(f"QSVC classification test score: {qsvc_score}")
QSVC classification test score: 1.0

Кластеризация

Для нашего примера кластеризации мы снова будем использовать набор данных ad hoc dataset из статьи Supervised learning with quantum enhanced feature spaces, и алгоритм кластеризации scikit-learn spectral.

Мы создадим набор данных с большим разрывом между двумя классами, и, поскольку кластеризация является заданием неконтролируемого (unsupervised) машинного обучения, нам не нужна тестовая выборка.

[7]:
adhoc_dimension = 2
train_features, train_labels, test_features, test_labels, adhoc_total = ad_hoc_data(
    training_size=25,
    test_size=0,
    n=adhoc_dimension,
    gap=0.6,
    plot_data=False,
    one_hot=False,
    include_sample_total=True,
)

plt.figure(figsize=(5, 5))
plt.ylim(0, 2 * np.pi)
plt.xlim(0, 2 * np.pi)
plt.imshow(
    np.asmatrix(adhoc_total).T,
    interpolation="nearest",
    origin="lower",
    cmap="RdBu",
    extent=[0, 2 * np.pi, 0, 2 * np.pi],
)
plt.scatter(
    train_features[np.where(train_labels[:] == 0), 0],
    train_features[np.where(train_labels[:] == 0), 1],
    marker="s",
    facecolors="w",
    edgecolors="b",
    label="A",
)
plt.scatter(
    train_features[np.where(train_labels[:] == 1), 0],
    train_features[np.where(train_labels[:] == 1), 1],
    marker="o",
    facecolors="w",
    edgecolors="r",
    label="B",
)

plt.legend(bbox_to_anchor=(1.05, 1), loc="upper left", borderaxespad=0.0)
plt.title("Ad hoc dataset for clustering")

plt.show()
../_images/tutorials_03_quantum_kernel_13_0.png

Мы снова настроим класс QuantumKernel для вычисления ядерной матрицы, используя ZFeatureMap, и BasicAer qasm_simulator с помощью 1024 вычислений.

[8]:
adhoc_feature_map = ZZFeatureMap(feature_dimension=adhoc_dimension, reps=2, entanglement="linear")

adhoc_backend = QuantumInstance(
    BasicAer.get_backend("qasm_simulator"), shots=1024, seed_simulator=seed, seed_transpiler=seed
)

adhoc_kernel = QuantumKernel(feature_map=adhoc_feature_map, quantum_instance=adhoc_backend)

Изучаемый спектральный алгоритм кластеризации позволяет нам определить [пользовательское ядро] двумя способами: путем предоставления ядра в качестве вызываемой функции или путем предварительного вычисления ядерной матрицы. Используя класс QuantumKernel в qiskit, мы можем использовать только второе.

Следующий код предварительно вычисляет и представляет в графическом виде ядерные матрицы перед передачей их в алгоритм спектральной кластеризации scikit-learn, и подсчитывает метки с помощью нормализованной общей информацию, так как мы априори знаем метки классов.

[9]:
adhoc_matrix = adhoc_kernel.evaluate(x_vec=train_features)

plt.figure(figsize=(5, 5))
plt.imshow(np.asmatrix(adhoc_matrix), interpolation="nearest", origin="upper", cmap="Greens")
plt.title("Ad hoc clustering kernel matrix")
plt.show()

adhoc_spectral = SpectralClustering(2, affinity="precomputed")
cluster_labels = adhoc_spectral.fit_predict(adhoc_matrix)
cluster_score = normalized_mutual_info_score(cluster_labels, train_labels)

print(f"Clustering score: {cluster_score}")
../_images/tutorials_03_quantum_kernel_17_0.png
Clustering score: 0.7287008798015754

scikit-learn имеет и другие алгоритмы, использующие предварительно рассчитанную ядерную матрицу. Вот некоторые из них:

[1]:
import qiskit.tools.jupyter

%qiskit_version_table
%qiskit_copyright

Version Information

Qiskit SoftwareVersion
qiskit-terra0.19.0
qiskit-aer0.8.2
qiskit-ignis0.6.0
qiskit-aqua0.9.2
qiskit0.27.0
qiskit-machine-learning0.3.0
System information
Python3.7.9 (default, Aug 31 2020, 17:10:11) [MSC v.1916 64 bit (AMD64)]
OSWindows
CPUs4
Memory (Gb)31.837730407714844
Fri Dec 03 15:08:20 2021 GMT Standard Time

This code is a part of Qiskit

© Copyright IBM 2017, 2021.

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.