Составить фоторобот онлайн на человека бесплатно
Содержание:
- Какие бывают электрогенераторы
- Как выбрать генератор
- Подготовка
- (6) Результаты
- Итак, что такое GAN?
- Как пользоваться генератором
- Манипулировать скрытыми векторами
- Основные операции линейной алгебры
- Итак, как это работает?
- (2) Подготовка данных
- (3) Определение модели
- оптимизаторы
- Генератор
- (4) Инициализировать вес ваших сетей
- (5) Построить полную сеть
Какие бывают электрогенераторы
Для бытового применения используется бензиновый генератор переменного тока. Он выдает достаточную мощность, чтобы обеспечить электроэнергией весь дом. Для этого вполне достаточно 5-10 киловатт мощности. Такие генераторы обойдутся в умеренную сумму.
Но не надо забывать, что бензин весьма дорогое топливо, а эксплуатировать бензиновый генератор длительное время не рекомендуется. Да этого и не нужно. Как правило, электричество отключают не более, чем на несколько дней и бензиновый двигатель с такой задачей справится.
Однако подобные установки чаще всего используются в промышленных целях, так как они могут вырабатывать повышенные объемы элетроэнергии.
Если дом большой и потребности выше, то лучше обеспечить себя генератором на 20-50 киловатт. Это, конечно же, с запасом.
Как выбрать генератор
Основные параметры мы уже рассмотрели, теперь углубимся в детали. Не стоит покупать генератор изучив только фото бензиновых генераторов на сайте продавца. Здесь не будет лишним поход в магазин. Необходимо обсудить с консультантом все особенности энергоснабжения Вашего дома и остановиться на самом оптимальном варианте.
Хороший продавец продемонстрирует устройство в действии, и Вы в результате приобретете то, что прослужит долгие годы.
Ценовой диапазон этих агрегатов весьма разнообразен. Не нужно излишне экономить и покупать некачественный товар. Электрический генератор приобретается на долгие годы.
Подготовка
Обучение будет включать чередование обучения дискриминатора и генератора. Мы будем использоватьreal_lossа такжеfake_lossфункции, определенные ранее, чтобы помочь нам в расчете потерь дискриминатора и генератора.
- Вы должны тренировать дискриминатор, чередуя реальные и поддельные изображения
- Тогда генератор, который пытается обмануть дискриминатор и должен иметь противоположную функцию потерь
Вот код для обучения.
def train(D, G, n_epochs, print_every=50): '''Trains adversarial networks for some number of epochs param, D: the discriminator network param, G: the generator network param, n_epochs: number of epochs to train for param, print_every: when to print and record the models' losses return: D and G losses''' # move models to GPU if train_on_gpu: D.cuda() G.cuda()# keep track of loss and generated, "fake" samples samples = [] losses = []# Get some fixed data for sampling. These are images that are held # constant throughout training, and allow us to inspect the model's performance sample_size=16 fixed_z = np.random.uniform(-1, 1, size=(sample_size, z_size)) fixed_z = torch.from_numpy(fixed_z).float() # move z to GPU if available if train_on_gpu: fixed_z = fixed_z.cuda()# epoch training loop for epoch in range(n_epochs):# batch training loop for batch_i, (real_images, _) in enumerate(celeba_train_loader):batch_size = real_images.size(0) real_images = scale(real_images) if train_on_gpu: real_images = real_images.cuda() # 1. Train the discriminator on real and fake ima.ges d_optimizer.zero_grad() d_out_real = D(real_images) z = np.random.uniform(-1,1,size = (batch_size,z_size)) z = torch.from_numpy(z).float() if train_on_gpu: z = z.cuda() d_loss = real_loss(d_out_real) + fake_loss(D(G(z))) d_loss.backward() d_optimizer.step() # 2. Train the generator with an adversarial loss G.train() g_optimizer.zero_grad() z = np.random.uniform(-1,1,size = (batch_size,z_size)) z = torch.from_numpy(z).float() if train_on_gpu: z = z.cuda() g_loss = real_loss(D(G(z))) g_loss.backward() g_optimizer.step() # Print some loss stats if batch_i % print_every == 0: # append discriminator loss and generator loss losses.append((d_loss.item(), g_loss.item())) # print discriminator and generator loss print('Epoch [{:5d}/{:5d}] | d_loss: {:6.4f} | g_loss: {:6.4f}'.format( epoch+1, n_epochs, d_loss.item(), g_loss.item()))## AFTER EACH EPOCH## # this code assumes your generator is named G, feel free to change the name # generate and save sample, fake images G.eval() # for generating samples samples_z = G(fixed_z) samples.append(samples_z) G.train() # back to training mode# Save training generator samples with open('train_samples.pkl', 'wb') as f: pkl.dump(samples, f) # finally return losses return losses# set number of epochs n_epochs = 40# call training functionlosses = train(D, G, n_epochs=n_epochs)
(6) Результаты
Ниже приведен график потерь обучения для Генератора и Дискриминатора, записанных после каждой эпохи.
Потеря обучения длядискриминатора такжеГенератор
Высокие флуктуации в обучающей потере генератора обусловлены тем, что вход в сеть генератора представляет собой набор случайных векторов шума(каждый из z_size)каждая выборка из равномерного распределения (-1,1) для генерации новых изображений для каждой эпохи.
На графике дискриминатора мы можем наблюдать рост тренировочной потери(около 50 на оси X)сопровождаемое постепенным уменьшением до конца, это потому, что Генератор начал генерировать какое-то реалистичное изображение, которое обмануло Дискриминатор, что привело к увеличению ошибки. Но постепенно по ходу обучения Discriminator становится лучше в классификации ложных и реальных изображений, что приводит к постепенному уменьшению ошибки обучения.
Сгенерированные образцы после40 эпох,
Сгенерированные поддельные изображения
Наша модель была в состоянии генерировать новые изображения поддельных человеческих лиц, которые выглядят максимально реалистично. Мы также можем заметить, что все изображения светлее в тени, даже коричневые лица немного светлее. Это потому чтоCelebAнабор данных смещен; он состоит из «знаменитостей», которые в основном белые. При этом DCGAN успешно генерирует почти реальные изображения из простого шума.
Итак, что такое GAN?
Чтобы упростить его, это один из методов глубокого обучения, который используется для создания новых данных с нуля. Он работает неконтролируемым образом, что означает, что он может работать без пометки человека. Это будет делать данные на основе шаблона, который он изучает
На GAN есть некоторые характеристики, которые являются генеративной моделью, а именно:
- Узнает совместную вероятностьР (х, у)гдеИксэто вход иYвыход. Это будет делать вывод на основеР (х | у), учитывая выходу,это выведетИкс.Вы можете сказать, чтоYэто реальные данные в ГАН.
- Когда модель дается обучение реальные данныеY, он узнает характеристику реальных данных. Это будет учиться путем выявления реальных данныхпеременная скрытого представления объекта, Чтобы упростить его, он изучает функцию базового конструктора изображений в реальных данных. Например, модель может узнать, что лица построены по цвету глаз и волос. Эти два будут одной из основ, которые будут использоваться при создании граней. Изменяя его переменную, он также может изменять сгенерированные грани. Например, подняв переменную глаза, глаза станут чернее. Понижение этого сделает противоположное иначе.
- Он может построить распределение вероятностей, такое как нормальное распределение, которое можно использовать для предотвращенияостанец, посколькуостанецкак правило, очень редко встречается в дистрибутиве, его очень редко генерируют. Таким образом, GAN хорошо работает с реальными данными, которые имеют выбросы.
Как пользоваться генератором
Чтобы генератор начал работать, его необходимо завести. Это можно сделать при помощи ручного стартера. Нужно сильно дернуть за веревочку. Если с двигателем какие-то проблемы или некачественное топливо, то подергать придется несколько раз. Эта процедура тоже не из разряда увлекательных.
Поэтому лучше купить генератор с электрическим стартером. Как только мотор заведется сразу можно подключать нагрузку. Есть варианты автоматического или полуавтоматического включения генератора. Лучше всего приобрести бензиновый генератор с автоматическим запуском.
Когда в Вашем доме отключится электричество генератор запустится сам и выключится самостоятельно при возобновлении подачи электроэнергии.
Манипулировать скрытыми векторами
Посмотрим, как будут создаваться изображения, если мы будем манипулировать измерением в скрытом векторе. Как я уже говорил ранее, модель научится скрытому представлению признаков. Итак, каждый элемент в скрытом векторе имеет своей целью генерацию изображения.
Чтобы сделать визуализацию, мы заморозим все элементы в векторах и изменим выбранное измерение, которое нужно проверить.
Изображения 18: Иллюстрация о том, что мы делаем в этом разделе
Например, мы хотим исследовать 1-й элемент в скрытом векторе, мы изменяем это измерение и оставляем остальные неизменными.
Мы сгенерируем несколько граней, которые имеют среднее значение в этих точках:
Для каждой средней точки мы сгенерируем грани, размер которых в скрытом векторе будет изменен с этими значениями итеративно:
Позвольте визуализировать на нашем выбранном измерении: (Этот раздел будет использовать только МОДЕЛЬ-A)
28-е измерение:
Изображение 19: Результат изменения 28-й скрытой переменной в разных средних точках.
Каковы цели 28-й скрытой переменной?
Я думаю, это делает волосы ярче, меняет форму левого глаза, а также небольшие изменения на правом глазу. Поскольку он сжимает элемент в скрытый вектор длиной 64, одно измерение может иметь несколько целей.
Давайте посмотрим еще один!
5-е измерение
Рисунок 20: Результат изменения 5-й скрытой переменной разными способами
Что это за скрытые переменные цели?
Я думаю, что это как-то связано с левыми глазами, даже несмотря на то, как левые глаза отличаются для каждой средней точки. Это также делает волосы немного темнее. Что вы думаете?
11-е измерение
Рисунок 21: Результат изменения 11-ых скрытых переменных различными способами
Я думаю, это измерение заботит рот и правый глаз.
Другой пример для граней, которые генерируются из средних точек только путем подстройки скрытой переменной:
Изображение 22: Результат на лицах путем изменения скрытой переменной
Это оно. Мы можем построить любые измерения в скрытых векторах и посмотреть, каковы их цели. Хотя иногда трудно понять, каковы цели скрытой переменной.
Основные операции линейной алгебры
Удивительно, не правда ли?
Пока нет, мы можем выполнить операцию линейной алгебры со скрытым вектором. Результат уравнения также может быть сгенерирован и иметь интересный результат. Возьмите результат от наших первых лиц перед вводным разделом:
G + D
Изображения 15: G + D = GAN
Ган лица является результатом добавления G с D. Вы можете видеть, что волосы становятся немного коричневыми. и волосы следуют за стилем D справа и G слева.
Ниже приведены результаты других операций:
G — D (Абсолют)
Изображения 16: G-D
Умножение по компонентам (G, D)
Изображения 17:Умножение по компонентам (G, D)
Итак, как это работает?
ГАН состоит из двух нейронных сетей,дискриминатора такжеГенератор, GAN заставит эти две сети сражаться друг с другом на игровой основе с нулевой суммой (теория игр). Это игра между этими агентами (сетями).состязательныйимя в GAN происходит от этой концепции.
Изображение 2: Иллюстрация Дискриминатор против Генератора. Изображение изменено и взято изВот
Генераторбудет генерировать некоторые поддельные данные идискриминаторбудет идентифицировать пару данных, которые имеют поддельные данные, сгенерированныеГенератори данные, взятые из реальных данных. ЦельГенераторв основном генерирует некоторые поддельные данные, которые предназначены аналогично реальным данным, и обманываетдискриминаторна выявление, какие данные являются реальными и поддельными. Цельдискриминаторэто сделать его умнее при выявлении реальных и поддельных данных. Каждый агент будет двигаться попеременно. Дуэли этих агентов, мы надеемся, что эти агенты станут сильнее, особенноГенератор.
Хорошо, другими словами,Генераторбудет имитировать реальные данные путем выборки распределения, которое изучено и предназначено для того же распределения, что и реальные данные. Он обучит свою нейронную сеть, которая может генерировать ее
Принимая во внимание, чтодискриминаторбудет обучать свою нейронную сеть контролируемой технике обнаружения поддельных и реальных данных. Каждая сеть будет обучать свою сеть попеременно
Рисунок 3: Иллюстрация GAN по распределению обучающих данных. Фото сделано сВот,
Вот грубые шаги о том, как работает GAN:
Генерировать случайный шум в распределении вероятностей, таких как нормальное распределение.
Сделайте это в качестве входного сигнала нашей нейронной сети генератора. Будет выведен сгенерированныйподдельные данные, Эти шаги также могут означать, что мы выбираем некоторые данные из дистрибутива, который узнал генератор. Мы отметим шум каки сгенерированные данные как,означает результат шума, обработанного генераторомг,
Мы объединяем сгенерированные поддельные данные с данными, которые взяты из набора данных (которые являются реальными данными). Сделайте их вкладом нашегоДискриминатор. Мы отметим это как D.Дискриминатор попытается узнать, предсказав, являются ли данные поддельными или нет. Обучите нейронную сеть, выполнив прямой проход и затем обратное распространение
ОбновляетDвеса.
Затем нам нужно тренироватьГенератор, Нам нужно сделатьили поддельные данные, сгенерированные из случайных шумов в качестве входаD.Обратите внимание, что эти шаги только вводят поддельные данные вдискриминатор, Вперед пройтивD.Используя нейронную сеть Discriminator, выполняя прямую передачу, предсказывайте, являются ли поддельные данные ложными или нет, Затем выполните обратное распространение, где мы будем только обновлятьгвеса.
Повторяйте эти шаги до тех пор, пока мы не увидим, что генератор предоставляет хорошие поддельные данные или не достигнута максимальная итерация.
Иллюстрация выглядит следующим образом:
Изображение 4: Как работает GAN. Фото сделано сВот,
Обновив дистрибутив Генератора, чтобы он соответствовал Дискриминатору. Это то же самое, что минимизировать расхождение JS. Для получения дополнительной информации вы можете прочитатьэтостатья.
Чтобы наши агенты научились, убедитесь, чтодискриминатора такжегенератордоминировать друг над другом. Сделайте их как можно более сбалансированными и сделайтедискриминатора такжегенераторучиться одновременно Когдадискриминаторявляется слишком сильным (может различать поддельные и настоящие 100%),Генераторстать неспособным слишком чему-то научиться. Если в процессе обучения мы дойдем до этой точки, лучше ее закончить. Противоположность также имеет эффект, когдаГенераторсильнее, чем дискриминатор. Это вызывает Mode Collapse, где наша модель всегда предсказывает один и тот же результат для любых случайных шумов. Это одна из самых сложных и трудных частей GAN, которая может расстроить кого-то.
Если вы хотите понять больше, я предлагаю взглянуть и прочитать это удивительноестатья,
(2) Подготовка данных
В качестве основной цели этой статьи является построениеDCGANмодели, поэтому вместо того, чтобы выполнять предварительную обработку самостоятельно, мы будем использовать предварительно обработанный набор данных. Вы можете скачать меньшее подмножествоCelebAнабор данных изВот, И если вы заинтересованы в предварительной обработке, сделайте следующее:
- Обрезать изображения, чтобы удалить часть, которая не включает лицо.
- Измените их размер на 64x64x3NumPyкартинки.
Теперь мы создадимDataLoaderдля доступа к изображениям в пакетном режиме.
def get_dataloader(batch_size, image_size, data_dir='train/'): """ Batch the neural network data using DataLoader :param batch_size: The size of each batch; the number of images in a batch :param img_size: The square size of the image data (x, y) :param data_dir: Directory where image data is located :return: DataLoader with batched data """ transform = transforms.Compose() dataset = datasets.ImageFolder(data_dir,transform = transform) dataloader = torch.utils.data.DataLoader(dataset = dataset,batch_size = batch_size,shuffle = True) return dataloader# Define function hyperparametersbatch_size = 256img_size = 32# Call your function and get a dataloaderceleba_train_loader = get_dataloader(batch_size, img_size)
DataLoaderгиперпараметры:
- Вы можете выбрать любой разумныйразмер партиипараметр.
- Тем не менее, вашРазмер изображениядолжно быть 32. Изменение размера данных до меньшего размера приведет к более быстрой тренировке, в то же время создавая убедительные изображения лиц.
Далее мы напишем некоторый код, чтобы получить визуальное представление набора данных.
def imshow(img): npimg = img.numpy() plt.imshow(np.transpose(npimg, (1, 2, 0)))# obtain one batch of training imagesdataiter = iter(celeba_train_loader)images, _ = dataiter.next() # _ for no labels# plot the images in the batch, along with the corresponding labelsfig = plt.figure(figsize=(20, 4))plot_size=20for idx in np.arange(plot_size): ax = fig.add_subplot(2, plot_size/2, idx+1, xticks=[], yticks=[]) imshow(images)
Имейте в виду, чтобы преобразоватьТензоризображения вNumPyвведите и транспонируйте размеры, чтобы правильно отобразить изображение на основе приведенного выше кода(В Dataloader мы преобразовали изображения в Tensor), Запустите этот фрагмент кода, чтобы получить визуализацию набора данных.
Изображения вокруг лиц
Теперь, прежде чем начать со следующего раздела(Определение модели),мы напишем функцию для масштабирования данных изображения в диапазоне пикселей от -1 до 1, которую мы будем использовать во время обучения. Причиной этого является то, что выходной сигнал активированного генератора будет содержать значения пикселей в диапазоне от -1 до 1, и поэтому нам необходимо изменить масштаб наших тренировочных изображений до диапазона от -1 до 1(сейчас они находятся в диапазоне 0–1),
def scale(x, feature_range=(-1, 1)): ''' Scale takes in an image x and returns that image, scaled with a feature_range of pixel values from -1 to 1. This function assumes that the input x is already scaled from 0-1.''' # assume x is scaled to (0, 1) # scale to feature_range and return scaled x min, max = feature_range x = x*(max-min) + min return x
(3) Определение модели
GANсостоит из двух противоборствующих сетей, дискриминатора и генератора. Итак, в этом разделе мы определим архитектуры для них обоих.
оптимизаторы
ДляGANs мы определяем два оптимизатора, один для генератора и другой для дискриминатора. Идея состоит в том, чтобы запустить их одновременно, чтобы продолжать улучшать обе сети. В этой реализации я использовалАдамоптимизаторв обоих случаях. Чтобы узнать больше о различных оптимизаторах, обратитесь к этомуссылка,
# Create optimizers for the discriminator D and generator Gd_optimizer = optim.Adam(D.parameters(),lr = .0002, betas = )g_optimizer = optim.Adam(G.parameters(),lr = .0002, betas = )
Скорость обучения (лр)а такжебетызначения основаны на оригиналеБумага DCGAN,
Генератор
Генератор должен сэмплировать входные данные и генерировать новое изображение того же размера, что и наши тренировочные данные 32X32X3. Для этого мы будем использовать транспонированные сверточные слои. Вот код для сети генератора.
def deconv(input_c,output,kernel_size,stride = 2, padding =1, batch_norm = True): layers = [] decon = nn.ConvTranspose2d(input_c,output,kernel_size,stride,padding,bias = False) layers.append(decon) if batch_norm: layers.append(nn.BatchNorm2d(output)) return nn.Sequential(*layers)class Generator(nn.Module): def __init__(self, z_size, conv_dim): """ Initialize the Generator Module :param z_size: The length of the input latent vector, z :param conv_dim: The depth of the inputs to the *last* transpose convolutional layer """ super(Generator, self).__init__() # complete init function self.conv_dim = conv_dim self.fc = nn.Linear(z_size,conv_dim*8*2*2) self.layer_1 = deconv(conv_dim*8,conv_dim*4,4) #4 self.layer_2 = deconv(conv_dim*4,conv_dim*2,4) #8 self.layer_3 = deconv(conv_dim*2,conv_dim,4) #16 self.layer_4 = deconv(conv_dim,3,4,batch_norm = False) #32 def forward(self, x): """ Forward propagation of the neural network :param x: The input to the neural network :return: A 32x32x3 Tensor image as output """ # define feedforward behavior x = self.fc(x) x = x.view(-1,self.conv_dim*8,2,2) #(batch_size,depth,width,height) x = F.relu(self.layer_1(x)) x = F.relu(self.layer_2(x)) x = F.relu(self.layer_3(x)) x = torch.tanh(self.layer_4(x)) return x
объяснение
- Следующая архитектура состоит из полностью связанного уровня, за которым следуют четыре уровня транспонирования свертки. Эта архитектура определена так, что выход после четвертого транспонированного слоя свертки приводит к изображению размера 32X32X3(размер изображения из набора обучающих данных).
- Входами в генератор являются векторы некоторой длиныz_size (z_size — вектор шума),
- Каждый слой транспонирования свертки, кроме последнего, сопровождаетсяПакетная нормализация (определена в вспомогательной функции deconv),
- Для скрытых юнитов мы использовалиРЕЛУфункция активации.
- После каждого транспонирования слоя свертки высота и ширина становятся двойными. Например, после первой транспонированной свертки изображения 2X2 будут изменены в 4X4 и так далее.
(4) Инициализировать вес ваших сетей
Чтобы помочь моделям сходиться, я инициализировал веса сверточного и линейного слоев в модели на основеоригиналDCGANбумага, который говорит: Все веса инициализируются из нормального распределения с нулевым центром со стандартным отклонением 0,02.
def weights_init_normal(m): """ Applies initial weights to certain layers in a model . The weights are taken from a normal distribution with mean = 0, std dev = 0.02. :param m: A module or layer in a network """ # classname will be something like: # `Conv`, `BatchNorm2d`, `Linear`, etc. classname = m.__class__.__name__ if hasattr(m,'weight') and (classname.find('Conv') != -1 or classname.find('Linear') != -1): m.weight.data.normal_(0.0,0.02) if hasattr(m,'bias') and m.bias is not None: m.bias.data.zero_()
- Это будет инициализировать веса к нормальному распределению, центрированному около 0, со стандартным отклонением 0,02.
- Термины смещения, если они существуют, могут быть оставлены в покое или установлены в 0.
(5) Построить полную сеть
Определите гиперпараметры ваших моделей и создайте экземпляр дискриминатора и генератора из классов, определенных вОпределение моделираздел. Вот код для этого.
def build_network(d_conv_dim, g_conv_dim, z_size): # define discriminator and generator D = Discriminator(d_conv_dim) G = Generator(z_size=z_size, conv_dim=g_conv_dim)# initialize model weights D.apply(weights_init_normal) G.apply(weights_init_normal)print(D) print() print(G) return D, G# Define model hyperparamsd_conv_dim = 64g_conv_dim = 64z_size = 100D, G = build_network(d_conv_dim, g_conv_dim, z_size)
Когда вы запустите приведенный выше код, вы получите следующий вывод. Также описывается архитектура модели для моделей дискриминатора и генератора.
конкретизированныхдискриминатора такжеГенератормодели