Эта статья проведет вас через процесс понимания графовых нейронных сетей (GNN) и их реализации с использованием TensorFlow. В последующей статье мы обсуждаем различные варианты GNN и их реализации. Вот пошаговый план:

  1. Использование графовых нейронных сетей (GNN). Мы начнем с обсуждения того, что такое GNN, как они работают и где используются.
  2. Понимание графов. Прежде чем мы углубимся в GNN, важно понять основы графов, включая узлы, ребра, матрицы смежности и представления графов.
  3. Понимание графовых нейронных сетей. Мы также кратко коснемся основ нейронных сетей, поскольку GNN — это тип нейронной сети.
  4. Варианты графовых нейронных сетей (GNN)
  5. Реализация GNN с помощью TensorFlow. Наконец, мы рассмотрим процесс реализации простой GNN с помощью TensorFlow.

Использование графовых нейронных сетей (GNN)

Нейронные сети графов (GNN) — это тип нейронных сетей, предназначенный для выполнения задач машинного обучения над структурами данных графов. Они особенно полезны для задач, где данные представлены в виде графиков, таких как социальные сети, молекулярные структуры и рекомендательные системы.

GNN работают, распространяя информацию от узла к его соседям. Узлы в графе обновляются в зависимости от состояния их соседей, и этот процесс повторяется несколько итераций. Затем конечное состояние узлов можно использовать для прогнозирования.

Например, в социальной сети GNN можно использовать для прогнозирования интересов пользователя на основе интересов его друзей. GNN начнет с некоторого начального представления каждого пользователя, а затем обновит представление каждого пользователя на основе представлений их друзей. После нескольких итераций окончательное представление каждого пользователя будет охватывать не только их собственные интересы, но и интересы их друзей, друзей их друзей и так далее.

Понимание графиков:

График – это математическая структура, которая моделирует отношения между объектами. Он состоит из узлов (также называемых вершинами) и ребер. Узлы представляют объекты, а ребра представляют отношения между этими объектами.

Например, в социальной сети каждый человек может быть представлен узлом, а каждая дружба может быть представлена ​​ребром, соединяющим два узла.

Существует два основных типа графиков:

  1. Неориентированные графы. В неориентированном графе ребра не имеют направления. То есть, если есть ребро от узла A к узлу B, есть также ребро от узла B к узлу A. Примером этого является дружба в Facebook: если человек A дружит с человеком B, то человек B также дружит с человеком А.
  2. Направленные графы. Ребра ориентированного графа имеют направление. То есть, если есть ребро от узла A к узлу B, это не обязательно означает, что есть ребро от узла B к узлу A. Примером этого является Twitter: если человек A следует за человеком B, он не означает, что человек B следует за человеком A.

Графики могут быть представлены несколькими способами, но один из наиболее распространенных – с помощью матрицы смежности. Матрица смежности — это квадратная матрица, в которой элемент в i-й строке и j-м столбце равен количеству ребер между вершинами i и j. Для неориентированного графа матрица смежности симметрична.

Другим распространенным представлением является список ребер, где каждое ребро представлено парой узлов.

Понимание этих основ графов имеет решающее значение для понимания того, как работают графовые нейронные сети, поскольку они работают непосредственно со структурой графа.

Понимание графовых нейронных сетей

GNN — это тип нейронной сети, предназначенный для выполнения задач машинного обучения на графовых структурах данных. Они особенно полезны для задач, где данные представлены в виде графиков, таких как социальные сети, молекулярные структуры и рекомендательные системы.

Ключевая идея GNN состоит в том, чтобы зафиксировать зависимости между соединениями в графе. Они делают это, объединяя функции соседних узлов для создания вложений для каждого узла. Затем эти вложения можно использовать для выполнения различных задач, таких как классификация узлов, предсказание ссылок и классификация графов.

Вот более подробный пошаговый процесс работы GNN:

  1. Инициализация функции узла. Каждый узел в графе инициализируется вектором функции. Это может быть однократное кодирование метки узла, некоторый действительный вектор, характерный для узла, или даже вектор нулей.
  2. Агрегация признаков: каждый узел объединяет векторы признаков соседних узлов для обновления собственного вектора признаков. Обычно это делается с помощью функции, которая принимает векторы признаков узла и его соседей и выводит новый вектор признаков. Функция может быть простой средней, взвешенной суммой или более сложной функцией.
  3. Преобразование признаков. Затем агрегированный вектор признаков преобразуется, как правило, с использованием линейного преобразования, за которым следует нелинейная функция активации. Это похоже на то, что происходит в традиционном слое нейронной сети.
  4. Повторить шаги 2 и 3. Шаги 2 и 3 повторяются определенное количество раз. С каждой итерацией узлы объединяют и преобразуют объекты из все большего и большего соседства.
  5. Чтение: после последней итерации функция считывания используется для агрегирования векторов признаков всех узлов в графе для получения выходных данных на уровне графа.

Прелесть GNN в том, что они могут обрабатывать графы различных размеров и форм, а также фиксировать локальную и глобальную структуру графа.

Реализация GNN с помощью TensorFlow

Существует несколько библиотек, построенных поверх TensorFlow, которые предоставляют реализации различных типов GNN, таких как Graph Nets и Spektral. Мы можем использовать одну из этих библиотек, чтобы упростить процесс реализации.

Во-первых, вам нужно установить библиотеку Spektral. Вы можете сделать это с помощью pip:

pip install spektral

После того, как вы установили Spektral, вы можете начать с импорта необходимых библиотек:

import numpy as np
import tensorflow as tf
from tensorflow.keras.models import Model
from tensorflow.keras.layers import Dense, Dropout
from spektral.layers import GCNConv, global_sum_pool
from spektral.data import DisjointLoader, Dataset
from spektral.datasets import TUDataset

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

Далее давайте загрузим набор данных:

dataset = TUDataset('PROTEINS')

Это загрузит набор данных PROTEINS, который представляет собой набор данных классификации графов белковых структур.

  1. Чтение: после последнего слоя функция считывания используется для агрегирования векторов признаков всех узлов в графе для получения выходных данных на уровне графа.

Теперь давайте посмотрим, как мы можем реализовать простую модель GraphSAGE, используя библиотеку Spektral в TensorFlow:

import spektral
from spektral.layers import GraphSageConv
from tensorflow.keras.models import Model
from tensorflow.keras.layers import Input, Dropout, Dense

# Define the model
class GraphSageModel(Model):
    def __init__(self, n_hidden, n_labels):
        super().__init__()
        self.sage_conv1 = GraphSageConv(n_hidden)
        self.sage_conv2 = GraphSageConv(n_labels)
        self.dropout = Dropout(0.5)
        self.dense = Dense(n_labels, 'softmax')

    def call(self, inputs, training=False):
        x, a = inputs
        x = self.dropout(x, training=training)
        x = self.sage_conv1([x, a])
        x = self.sage_conv2([x, a])
        return self.dense(x)

# Instantiate the model
model = GraphSageModel(n_hidden=64, n_labels=dataset.n_labels)

Эта модель принимает в качестве входных данных граф, представленный его узловыми функциями x, матрицей смежности a и пакетным индексом i. Модель сначала применяет отсев к функциям узла, затем применяет два слоя свертки графа, объединяет функции узла в представление на уровне графа и, наконец, применяет плотный слой для прогнозирования класса каждого графа.

Далее скомпилируем и обучим нашу модель:

model = GNN(n_hidden=64, n_labels=dataset.n_labels)
model.compile('adam', 'categorical_crossentropy', ['acc'])
loader = DisjointLoader(dataset, batch_size=32, epochs=10)
model.fit(loader.load(), steps_per_epoch=loader.steps_per_epoch)

что значит global_sum_pool represent?

В контексте графовых нейронных сетей (GNN) объединение — это метод, используемый для объединения информации из всего графа в единое векторное представление. Это особенно полезно для задач прогнозирования на уровне графа, когда мы хотим сделать прогноз для всего графа (в отличие от отдельных узлов или ребер).

global_sum_pool — одна из таких операций объединения, предоставляемая библиотекой Spektral. Как следует из названия, он просто суммирует векторы признаков всех узлов в графе для получения единого вектора. Эта операция инвариантна к порядку узлов в графе, что является важным свойством для многих задач на основе графа.

Стоит отметить, что объединение сумм — это очень простая операция объединения, и существует множество других более сложных операций объединения, которые можно использовать в GNN, таких как объединение средних значений, объединение максимальных значений и более сложные методы, такие как объединение графов внимания и объединение изоморфизмов графов. Выбор операции объединения может существенно повлиять на производительность GNN, и лучший выбор часто зависит от конкретной задачи и данных.

Что i обозначает x = self.pool(x, i)?

i в вызове функции global_sum_pool(x, i) представляет пакетный индекс для каждого узла.

Когда вы работаете с данными графика в пакетном режиме (т. е. с несколькими графиками в одном пакете), вам нужен способ указать, какие узлы к каким графикам относятся. Это связано с тем, что, в отличие от изображений или текстовых данных, графы в пакете могут иметь разные размеры (т. е. разное количество узлов и ребер), поэтому вы не можете просто сложить их в один тензор.

Индекс пакета i — это вектор, который назначает каждый узел определенному графу в пакете. Например, если у вас есть два графика в пакете, первый с 3 узлами, а второй с 2 ​​узлами, индекс вашего пакета i будет [0, 0, 0, 1, 1]. Это указывает на то, что первые три узла принадлежат первому графу, а последние два узла принадлежат второму графу.

В последующей статье мы обсуждаем различные варианты GNN и их реализации.