Модели и слои

В машинном обучении модель — это функция с обучаемыми параметрами , которая сопоставляет входные данные с выходными данными. Оптимальные параметры получаются путем обучения модели на данных. Хорошо обученная модель обеспечит точное сопоставление входных данных с желаемыми выходными данными.

В TensorFlow.js есть два способа создания модели машинного обучения:

  1. используя Layers API, где вы строите модель, используя слои .
  2. использование Core API с операциями более низкого уровня, такими как tf.matMul() , tf.add() и т. д.

Сначала мы рассмотрим Layers API, который представляет собой API более высокого уровня для построения моделей. Затем мы покажем, как построить ту же модель с помощью Core API.

Создание моделей с помощью Layers API

Существует два способа создания модели с использованием Layers API: последовательная модель и функциональная модель. В следующих двух разделах каждый тип рассматривается более подробно.

Последовательная модель

Наиболее распространенным типом модели является Sequential модель, представляющая собой линейный набор слоев. Вы можете создать Sequential модель, передав список слоев в функцию sequential() :

const model = tf.sequential({
 layers: [
   tf.layers.dense({inputShape: [784], units: 32, activation: 'relu'}),
   tf.layers.dense({units: 10, activation: 'softmax'}),
 ]
});

Или через метод add() :

const model = tf.sequential();
model.add(tf.layers.dense({inputShape: [784], units: 32, activation: 'relu'}));
model.add(tf.layers.dense({units: 10, activation: 'softmax'}));

ВАЖНО: первому слою модели требуется inputShape . Обязательно исключите размер пакета при предоставлении inputShape . Например, если вы планируете передать тензоры модели формы [B, 784] , где B может быть любым размером пакета, при создании модели укажите inputShape как [784] .

Вы можете получить доступ к слоям модели через model.layers , а точнее через model.inputLayers и model.outputLayers .

Функциональная модель

Другой способ создать LayersModel — использовать функцию tf.model() . Ключевое различие между tf.model() и tf.sequential() заключается в том, что tf.model() позволяет создавать произвольный граф слоев, если они не имеют циклов.

Вот фрагмент кода, который определяет ту же модель, что и выше, с использованием API tf.model() :

// Create an arbitrary graph of layers, by connecting them
// via the apply() method.
const input = tf.input({shape: [784]});
const dense1 = tf.layers.dense({units: 32, activation: 'relu'}).apply(input);
const dense2 = tf.layers.dense({units: 10, activation: 'softmax'}).apply(dense1);
const model = tf.model({inputs: input, outputs: dense2});

Мы вызываем apply() для каждого слоя, чтобы соединить его с выходными данными другого слоя. Результатом apply() в этом случае является SymbolicTensor , который действует как Tensor , но без каких-либо конкретных значений.

Обратите внимание, что в отличие от последовательной модели мы создаем SymbolicTensor с помощью tf.input() вместо предоставления inputShape первому слою.

apply() также может дать вам конкретный Tensor , если вы передадите ему конкретный Tensor :

const t = tf.tensor([-2, 1, 0, 5]);
const o = tf.layers.activation({activation: 'relu'}).apply(t);
o.print(); // [0, 1, 0, 5]

Это может быть полезно при изолированном тестировании слоев и просмотре их результатов.

Как и в последовательной модели, вы можете получить доступ к слоям модели через model.layers , а точнее через model.inputLayers и model.outputLayers .

Проверка

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

Краткое описание модели

Вызовите model.summary() , чтобы распечатать полезную сводку модели, которая включает в себя:

  • Имя и тип всех слоев модели.
  • Выходная форма для каждого слоя.
  • Количество весовых параметров каждого слоя.
  • Если модель имеет общую топологию (обсуждаемую ниже), входные данные получает каждый слой.
  • Общее количество обучаемых и необучаемых параметров модели.

Для модели, которую мы определили выше, мы получаем на консоли следующий вывод:

Слой (тип) Выходная форма Парам #
плотный_Dense1 (Плотный) [ноль, 32] 25120
плотный_Dense2 (Плотный) [ноль, 10] 330
Всего параметров: 25450
Обучаемые параметры: 25450
Необучаемые параметры: 0

Обратите внимание на null значения в выходных формах слоев: напоминание о том, что модель ожидает, что входные данные будут иметь размер пакета в качестве самого внешнего измерения, что в данном случае может быть гибким из-за null значения.

Сериализация

Одним из основных преимуществ использования LayersModel по сравнению с API более низкого уровня является возможность сохранять и загружать модель. LayersModel знает о:

  • архитектура модели, позволяющая воссоздать модель.
  • вес модели
  • конфигурация обучения (потери, оптимизатор, метрики).
  • состояние оптимизатора, позволяющее возобновить обучение.

Чтобы сохранить или загрузить модель, достаточно одной строки кода:

const saveResult = await model.save('localstorage://my-model-1');
const model = await tf.loadLayersModel('localstorage://my-model-1');

В приведенном выше примере модель сохраняется в локальном хранилище браузера. См. model.save() documentation и руководство по сохранению и загрузке , чтобы узнать, как сохранять на разные носители (например, файловое хранилище, IndexedDB , запускать загрузку браузера и т. д.).

Пользовательские слои

Слои — это строительные блоки модели. Если ваша модель выполняет пользовательские вычисления, вы можете определить собственный слой, который хорошо взаимодействует с остальными слоями. Ниже мы определяем пользовательский слой, который вычисляет сумму квадратов:

class SquaredSumLayer extends tf.layers.Layer {
 constructor() {
   super({});
 }
 // In this case, the output is a scalar.
 computeOutputShape(inputShape) { return []; }

 // call() is where we do the computation.
 call(input, kwargs) { return input.square().sum();}

 // Every layer needs a unique name.
 getClassName() { return 'SquaredSum'; }
}

Чтобы проверить это, мы можем вызвать метод apply() с конкретным тензором:

const t = tf.tensor([-2, 1, 0, 5]);
const o = new SquaredSumLayer().apply(t);
o.print(); // prints 30

ВАЖНО: Если вы добавите пользовательский слой, вы потеряете возможность сериализовать модель.

Создание моделей с помощью Core API

В начале этого руководства мы упомянули, что существует два способа создания модели машинного обучения в TensorFlow.js.

Общее эмпирическое правило — всегда сначала стараться использовать Layers API, поскольку он создан по образцу широко распространенного API Keras, который следует передовым практикам и снижает когнитивную нагрузку . Layers API также предлагает различные готовые решения, такие как инициализация веса, сериализация модели, обучение мониторингу, переносимость и проверка безопасности.

Вы можете использовать Core API всякий раз, когда:

  • Вам нужна максимальная гибкость и контроль.
  • Вам не нужна сериализация или вы можете реализовать собственную логику сериализации.

Модели в Core API — это просто функции, которые принимают один или несколько Tensors и возвращают Tensor . Та же модель, что и выше, написанная с использованием Core API, выглядит следующим образом:

// The weights and biases for the two dense layers.
const w1 = tf.variable(tf.randomNormal([784, 32]));
const b1 = tf.variable(tf.randomNormal([32]));
const w2 = tf.variable(tf.randomNormal([32, 10]));
const b2 = tf.variable(tf.randomNormal([10]));

function model(x) {
  return x.matMul(w1).add(b1).relu().matMul(w2).add(b2).softmax();
}

Обратите внимание, что в Core API мы отвечаем за создание и инициализацию весов модели. Каждый вес поддерживается Variable , которая сигнализирует TensorFlow.js о том, что эти тензоры можно изучить. Вы можете создать Variable , используя tf.variable() и передав существующий Tensor .

В этом руководстве вы ознакомились с различными способами создания модели с использованием слоев и основного API. Далее см. руководство по обучению моделей , чтобы узнать, как обучать модель.