05 июля 2021

πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π Π°Π·Ρ€Π°Π±ΠΎΡ‚Ρ‡ΠΈΠΊ ПО (систСмы PDM/PLM) с 1993 Π³ΠΎΠ΄Π°, компания "Π˜ΠΠ’Π•Π ΠœΠ•Π₯" (www.intermech.ru). Π’ 2020-ΠΌ ΡƒΡΠΏΠ΅ΡˆΠ½ΠΎ Π·Π°ΠΊΠΎΠ½Ρ‡ΠΈΠ» курсы "ΠžΡΠ½ΠΎΠ²Ρ‹ Data Science" (минская IT Academy) Π Π΅Ρ„Π΅Ρ€Π΅Π½Ρ‚-ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Ρ‡ΠΈΠΊ тСхничСской Π»ΠΈΡ‚Π΅Ρ€Π°Ρ‚ΡƒΡ€Ρ‹ с английского языка.
ΠŸΡ€Π°ΠΊΡ‚ΠΈΡ‡Π΅ΡΠΊΠΎΠ΅ руководство Π² стилС "сдСлай сам" с Ρ€Π°Π±ΠΎΡ‚Π°ΡŽΡ‰ΠΈΠΌ ΠΊΠΎΠ΄ΠΎΠΌ создания ΠΈ обучСния VAE для Π»ΠΈΡ† знамСнитостСй Π½Π° Keras.
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство
ВСкст публикуСтся Π² ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄Π΅, Π°Π²Ρ‚ΠΎΡ€ ΡΡ‚Π°Ρ‚ΡŒΠΈ – МишСль Кана.

Π­Ρ‚Π° ΡΡ‚Π°Ρ‚ΡŒΡ ΠΏΠΎΠ·Π½Π°ΠΊΠΎΠΌΠΈΡ‚ вас со всСм Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΡ‹ΠΌ для Π½Π°Ρ‡Π°Π»Π° Ρ€Π°Π±ΠΎΡ‚Ρ‹ с Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΈΠ²Π½Ρ‹ΠΌΠΈ модСлями. ΠœΡ‹ прСдоставим пошаговоС руководство ΠΏΠΎ ΠΎΠ±ΡƒΡ‡Π΅Π½ΠΈΡŽ условных VAE Π½Π° Π½Π°Π±ΠΎΡ€Π°Ρ… Π΄Π°Π½Π½Ρ‹Ρ… с большими изобраТСниями ΠΈ ΠΈΡ… ΠΏΡ€ΠΈΠΌΠ΅Π½Π΅Π½ΠΈΡŽ для Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ Π½ΠΎΠ²Ρ‹Ρ… Ρ€Π°Π·ΠΌΠ΅Ρ‡Π΅Π½Π½Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ.

ΠœΠΎΡ‚ΠΈΠ²Π°Ρ†ΠΈΡ

Π—Π°Ρ‡Π΅ΠΌ Π½ΡƒΠΆΠ½ΠΎ Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π½ΠΎΠ²Ρ‹Π΅ Π΄Π°Π½Π½Ρ‹Π΅, Ссли Π² ΠΌΠΈΡ€Π΅ ΠΈ Ρ‚Π°ΠΊ ΠΎΠ³Ρ€ΠΎΠΌΠ½ΠΎΠ΅ количСство Π΄Π°Π½Π½Ρ‹Ρ…? Богласно IDC, Π² ΠΌΠΈΡ€Π΅ Π±ΠΎΠ»Π΅Π΅ 18 Π·Π΅Ρ‚Ρ‚Π°Π±Π°ΠΉΡ‚ΠΎΠ² Π΄Π°Π½Π½Ρ‹Ρ….

Π‘ΠΎΠ»ΡŒΡˆΠΈΠ½ΡΡ‚Π²ΠΎ Π·Π°Π΄Π°Ρ‡ машинного обучСния Ρ‚Ρ€Π΅Π±ΡƒΡŽΡ‚ Ρ€Π°Π·ΠΌΠ΅Ρ‡Π΅Π½Π½Ρ‹Ρ… Π΄Π°Π½Π½Ρ‹Ρ…, Π° ΠΏΠΎΠ»ΡƒΡ‡ΠΈΡ‚ΡŒ высококачСствСнныС Ρ€Π°Π·ΠΌΠ΅Ρ‡Π΅Π½Π½Ρ‹Π΅ Π΄Π°Π½Π½Ρ‹Π΅ слоТно. Если ΠΌΡ‹ Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΡƒΠ΅ΠΌ Π΄Π°Π½Π½Ρ‹Π΅ сами, ΠΌΡ‹ всСгда ΠΌΠΎΠΆΠ΅ΠΌ ΡΠ΄Π΅Π»Π°Ρ‚ΡŒ ΠΈΡ… ΡΡ‚ΠΎΠ»ΡŒΠΊΠΎ, сколько потрСбуСтся. НовыС Π΄Π°Π½Π½Ρ‹Π΅ ΠΌΠΎΠ³ΡƒΡ‚ Π½Π°Ρ‚ΠΎΠ»ΠΊΠ½ΡƒΡ‚ΡŒ вас Π½Π° Π½ΠΎΠ²Ρ‹Π΅ ΠΈΠ΄Π΅ΠΈ ΠΈ ΠΏΡ€Π΅Π΄ΠΎΡΡ‚Π°Π²ΠΈΡ‚ΡŒ Π½ΠΎΠ²Ρ‹Π΅ возмоТности.

Как ΡΠ³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ изобраТСния, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… Π½ΠΈΠΊΡ‚ΠΎ Π½Π΅ Π²ΠΈΠ΄Π΅Π»?

ΠŸΡ€ΠΎΡ‡ΠΈΡ‚Π°Π² эту ΡΡ‚Π°Ρ‚ΡŒΡŽ, Π²Ρ‹ ΡƒΠ·Π½Π°Π΅Ρ‚Π΅, Ρ‡Ρ‚ΠΎ Ρ‚Π°ΠΊΠΎΠ΅ Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹ΠΉ АвтоэнкодСр, ΠΈ ΠΊΠ°ΠΊ ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ ваш собствСнный для Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ Π½ΠΎΠ²Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π½ΠΈΠΊΡ‚ΠΎ Π½ΠΈΠΊΠΎΠ³Π΄Π° Π½Π΅ Π²ΠΈΠ΄Π΅Π». ΠœΡ‹ объясним ΠΈΠ΄Π΅ΠΈ ΠΈ ΠΊΠΎΠ½Ρ†Π΅ΠΏΡ†ΠΈΠΈ, Π»Π΅ΠΆΠ°Ρ‰ΠΈΠ΅ Π² Π΅Π³ΠΎ основС, Π±Π΅Π· ΠΊΠ°ΠΊΠΎΠΉ-Π»ΠΈΠ±ΠΎ ΠΌΠ°Ρ‚Π΅ΠΌΠ°Ρ‚ΠΈΠΊΠΈ.

ΠŸΡ€ΠΈΠΌΠ΅Ρ€ изобраТСния ΠΈ Π΅Π³ΠΎ рСконструкции с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ нашСго ΠΊΠΎΠ΄Π° VAE
ΠŸΡ€ΠΈΠΌΠ΅Ρ€ изобраТСния ΠΈ Π΅Π³ΠΎ рСконструкции с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ нашСго ΠΊΠΎΠ΄Π° VAE

Π”Π°Π½Π½Ρ‹Π΅

ΠœΡ‹ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌ подмноТСство ΡˆΠΈΡ€ΠΎΠΊΠΎ извСстного Π½Π°Π±ΠΎΡ€Π° Π΄Π°Π½Π½Ρ‹Ρ… ЗнамСнитостСй, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ ΠΏΠΎΠΌΠΎΠΆΠ΅Ρ‚ Π½Π°ΠΌ ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ модСль Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ Π»ΠΈΡ†. Π­Ρ‚ΠΎΡ‚ Π½Π°Π±ΠΎΡ€ ΠΌΠΎΠΆΠ½ΠΎ ΡΠΊΠ°Ρ‡Π°Ρ‚ΡŒ с сайта CelebFacesA. Он прСдоставляСт большой Π½Π°Π±ΠΎΡ€ Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ΠΎΠ² Π»ΠΈΡ†, содСрТащий Π±ΠΎΠ»Π΅Π΅ 200 тысяч ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ знамСнитостСй, для ΠΊΠ°ΠΆΠ΄ΠΎΠ³ΠΎ ΠΈΠ· ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… ΡƒΠΊΠ°Π·Π°Π½ΠΎ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ 40 Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ΠΎΠ².

  • 10.177 личностСй;
  • 202.599 ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ;
  • 5 Π²Π°ΠΆΠ½Π΅ΠΉΡˆΠΈΡ… Π»ΠΎΠΊΠ°Ρ†ΠΈΠΉ;
  • 40 Π±ΠΈΠ½Π°Ρ€Π½Ρ‹Ρ… Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ΠΎΠ² для ΠΊΠ°ΠΆΠ΄ΠΎΠ³ΠΎ изобраТСния.
        import pandas as pd

df_celeb = pd.read_csv('list_attr_celeba.csv')
df_celeb.head()
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

НиТС ΠΌΡ‹ Π²Ρ‹Π±ΠΈΡ€Π°Π΅ΠΌ случайныС Π»ΠΈΡ†Π° ΠΈ Π²Ρ‹Π²ΠΎΠ΄ΠΈΠΌ ΠΈΡ… ΠΌΠ΅Ρ‚Π°Π΄Π°Π½Π½Ρ‹Π΅ (Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚Ρ‹). Π˜Π·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΡ ΠΈΠΌΠ΅ΡŽΡ‚ высоту 218 пиксСлСй, ΡˆΠΈΡ€ΠΈΠ½Ρƒ 178 пиксСлСй ΠΈ 3 Ρ†Π²Π΅Ρ‚ΠΎΠ²Ρ‹Ρ… ΠΊΠ°Π½Π°Π»Π°.

        import matplotlib.pyplot as plt
import random
from skimage.io import imread

def show_sample_image(nb=3, df=df_celeb, verbose=True):
    f, ax = plt.subplots(1, nb, figsize=(10,5))
    for i in range(nb):
        idx = random.randint(0, df.shape[0]-1)
        img_id = df.loc[idx].image_id
        img_uri = 'img_align_celeba/' + img_id
        img = skimage.io.imread(img_uri)  
        if verbose:
            label = img_id
            for col in df.columns:
                if df.loc[idx][col]==1:
                    label = label + '\n' + col  
            if nb > 1:
                ax[i].imshow(img)
                ax[i].set_title(label)
            else:
                ax.imshow(img) 
                ax.set_title(label)
        
    return img, list(df.loc[idx][1:df.shape[1]])
  
sample_img, sample_img_meta = show_sample_image()
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π§Ρ‚ΠΎ Ρ‚Π°ΠΊΠΎΠ΅ автоэнкодСр (AE)?

ΠŸΡ€ΠΎΡΠΌΠΎΡ‚Ρ€Π΅Π² Π»ΠΈΡ†Π° тысяч знамСнитостСй, нСйронная ΡΠ΅Ρ‚ΡŒ ΠΌΠΎΠΆΠ΅Ρ‚ Π½Π°ΡƒΡ‡ΠΈΡ‚ΡŒΡΡ Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π»ΠΈΡ†Π° людСй, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… Π½Π΅ сущСствуСт.

НСйронныС сСти – это ΠΎΠ΄ΠΈΠ½ ΠΈΠ· мноТСства Π²ΠΎΠ·ΠΌΠΎΠΆΠ½Ρ‹Ρ… ΠΌΠ΅Ρ‚ΠΎΠ΄ΠΎΠ², ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ для аппроксимации (приблиТСния) Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ. ΠŸΡ€ΠΈΡ‡ΠΈΠ½Π° ΠΈΡ… популярности – ΠΈΡ… ΡΠΏΠΎΡΠΎΠ±Π½ΠΎΡΡ‚ΡŒ ΡƒΡΠ²Π°ΠΈΠ²Π°Ρ‚ΡŒ прСдставлСния. НСйронныС сСти ΠΌΠΎΠ³ΡƒΡ‚ ΠΈΠ·ΡƒΡ‡ΠΈΡ‚ΡŒ Ρ‚Π΅ прСдставлСния, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ ΠΈΠΌΠ΅ΡŽΡ‚ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ для Ρ‚ΠΎΠ³ΠΎ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ Ρ€Π°Π·Π»ΠΈΡ‡Π°Ρ‚ΡŒ изобраТСния кошСк ΠΈ собак, Ссли ΠΌΡ‹ прСдоставим ΠΈΠΌ ΠΏΡ€Π°Π²ΠΈΠ»ΡŒΠ½ΠΎ Ρ€Π°Π·ΠΌΠ΅Ρ‡Π΅Π½Π½Ρ‹Π΅ Π΄Π°Π½Π½Ρ‹Π΅. Π­Ρ‚ΠΎ ΠΎΠ±ΡƒΡ‡Π΅Π½ΠΈΠ΅ с ΡƒΡ‡ΠΈΡ‚Π΅Π»Π΅ΠΌ.

Иногда этих ΠΌΠ΅Ρ‚ΠΎΠΊ Ρƒ нас Π½Π΅Ρ‚. Π’Π΅ΠΌ Π½Π΅ ΠΌΠ΅Π½Π΅Π΅, ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ ΠΎΠ±ΡƒΡ‡ΠΈΡ‚ΡŒ Π΄Π²Π΅ Π½Π΅ΠΉΡ€ΠΎΠ½Π½Ρ‹Π΅ сСти – ΠΎΠ΄Π½Π° Π±ΡƒΠ΄Π΅Ρ‚ ΡƒΡΠ²Π°ΠΈΠ²Π°Ρ‚ΡŒ прСдставлСниС, Π° вторая – Π²ΠΎΡΡΡ‚Π°Π½Π°Π²Π»ΠΈΠ²Π°Ρ‚ΡŒ исходноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ ΠΈΠ· этого прСдставлСния, минимизируя Ρ„ΡƒΠ½ΠΊΡ†ΠΈΡŽ ΠΏΠΎΡ‚Π΅Ρ€ΡŒ рСконструкции. Π­Ρ‚ΠΎ автоэнкодСр (Π°Π²Ρ‚ΠΎΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Ρ‰ΠΈΠΊ). Он Ρ‚Π°ΠΊ называСтся ΠΏΠΎΡ‚ΠΎΠΌΡƒ, Ρ‡Ρ‚ΠΎ автоматичСски Π½Π°Ρ…ΠΎΠ΄ΠΈΡ‚ Π»ΡƒΡ‡ΡˆΠΈΠΉ способ Π·Π°ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π΄Π°Π½Π½Ρ‹Π΅ Ρ‚Π°ΠΊ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ дСкодированная вСрсия Π±Ρ‹Π»Π° ΠΊΠ°ΠΊ ΠΌΠΎΠΆΠ½ΠΎ Π±Π»ΠΈΠΆΠ΅ ΠΊ исходной.

АвтоэнкодСр состоит ΠΈΠ· Π΄Π²ΡƒΡ… соСдинСнных Π½Π΅ΠΉΡ€ΠΎΠ½Π½Ρ‹Ρ… сСтСй: ΠΌΠΎΠ΄Π΅Π»ΠΈ энкодСра (ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Ρ‰ΠΈΠΊΠ°) ΠΈ ΠΌΠΎΠ΄Π΅Π»ΠΈ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€Π° (Π΄Π΅ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Ρ‰ΠΈΠΊΠ°). Π•Π³ΠΎ Ρ†Π΅Π»ΡŒ – Π½Π°Ρ…ΠΎΠΆΠ΄Π΅Π½ΠΈΠ΅ ΠΌΠ΅Ρ‚ΠΎΠ΄Π° кодирования Π»ΠΈΡ† знамСнитостСй Π² ΡΠΆΠ°Ρ‚ΡƒΡŽ Ρ„ΠΎΡ€ΠΌΡƒ (скрытоС пространство) Ρ‚Π°ΠΊΠΈΠΌ ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ восстановлСнная вСрсия Π±Ρ‹Π»Π° ΠΊΠ°ΠΊ ΠΌΠΎΠΆΠ½ΠΎ Π±Π»ΠΈΠΆΠ΅ ΠΊ Π²Ρ…ΠΎΠ΄Π½ΠΎΠΉ.

Как Ρ€Π°Π±ΠΎΡ‚Π°ΡŽΡ‚ ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Ρ‹ автоэнкодСра
Как Ρ€Π°Π±ΠΎΡ‚Π°ΡŽΡ‚ ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Ρ‹ автоэнкодСра
  • МодСль энкодСра ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ΠΈΡ‚ Π²Ρ…ΠΎΠ΄Π½ΠΎΠ΅ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ X Π² малСнькоС ΠΏΠ»ΠΎΡ‚Π½ΠΎΠ΅ прСдставлСниС Z, ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π½ΠΎ Ρ‚Π°ΠΊ ΠΆΠ΅, ΠΊΠ°ΠΊ Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚ свСрточная нСйронная ΡΠ΅Ρ‚ΡŒ, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ Ρ„ΠΈΠ»ΡŒΡ‚Ρ€Ρ‹ для усвоСния прСдставлСний.
  • МодСль Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€Π° ΠΌΠΎΠΆΠ½ΠΎ ΡΡ‡ΠΈΡ‚Π°Ρ‚ΡŒ Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΈΠ²Π½ΠΎΠΉ модСлью, способной Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ спСцифичСскиС ΠΏΡ€ΠΈΠ·Π½Π°ΠΊΠΈ X'.
  • Π­Π½ΠΊΠΎΠ΄Π΅Ρ€ ΠΈ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€ ΠΎΠ±Ρ‹Ρ‡Π½ΠΎ ΠΎΠ±ΡƒΡ‡Π°ΡŽΡ‚ΡΡ вмСстС. Ѐункция ΠΏΠΎΡ‚Π΅Ρ€ΡŒ ΡˆΡ‚Ρ€Π°Ρ„ΡƒΠ΅Ρ‚ ΠΎΠ±ΡŠΠ΅Π΄ΠΈΠ½Π΅Π½Π½ΡƒΡŽ ΡΠ΅Ρ‚ΡŒ Π·Π° созданиС Π²Ρ‹Ρ…ΠΎΠ΄Π½Ρ‹Ρ… Π»ΠΈΡ†, ΠΎΡ‚Π»ΠΈΡ‡Π°ΡŽΡ‰ΠΈΡ…ΡΡ ΠΎΡ‚ Π²Ρ…ΠΎΠ΄Π½Ρ‹Ρ… Π»ΠΈΡ†.

Π’Π°ΠΊΠΈΠΌ ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ, энкодСр обучаСтся ΡΠΎΡ…Ρ€Π°Π½ΡΡ‚ΡŒ ΠΊΠ°ΠΊ ΠΌΠΎΠΆΠ½ΠΎ большС ΠΏΠΎΠ»Π΅Π·Π½ΠΎΠΉ ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΠΈ Π² скрытом пространствС ΠΈ Ρ€Π°Π·ΡƒΠΌΠ½ΠΎ ΠΎΡ‚Π±Ρ€Π°ΡΡ‹Π²Π°Ρ‚ΡŒ Π½Π΅Π²Π°ΠΆΠ½ΡƒΡŽ ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΡŽ – Π½Π°ΠΏΡ€ΠΈΠΌΠ΅Ρ€, ΡˆΡƒΠΌ. Π”Π΅ΠΊΠΎΠ΄Π΅Ρ€ обучаСтся ΠΏΡ€Π΅Π²Ρ€Π°Ρ‰Π°Ρ‚ΡŒ ΡΠΆΠ°Ρ‚ΡƒΡŽ ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΡŽ Π² скрытом пространствС Π² Ρ†Π΅Π»ΠΎΠ΅ Π»ΠΈΡ†ΠΎ знамСнитости.

АвтоэнкодСры Ρ‚Π°ΠΊΠΆΠ΅ ΠΌΠΎΠ³ΡƒΡ‚ Π±Ρ‹Ρ‚ΡŒ ΠΏΠΎΠ»Π΅Π·Π½Ρ‹ΠΌΠΈ для сокращСния размСрности ΠΈ удалСния ΡˆΡƒΠΌΠΎΠ², ΠΈ ΠΌΠΎΠ³ΡƒΡ‚ ΠΎΡ‡Π΅Π½ΡŒ ΡƒΡΠΏΠ΅ΡˆΠ½ΠΎ ΠΏΡ€ΠΎΠ²ΠΎΠ΄ΠΈΡ‚ΡŒ ΠΌΠ°ΡˆΠΈΠ½Π½Ρ‹ΠΉ ΠΏΠ΅Ρ€Π΅Π²ΠΎΠ΄ Π±Π΅Π· учитСля.

Π§Ρ‚ΠΎ Ρ‚Π°ΠΊΠΎΠ΅ Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹ΠΉ автоэнкодСр (VAE)?

Как ΠΏΡ€Π°Π²ΠΈΠ»ΠΎ, скрытоС пространство Z, создаваСмоС энкодСром, Ρ€Π΅Π΄ΠΊΠΎ засСлСно, Ρ‚ΠΎ Π΅ΡΡ‚ΡŒ Ρ‚Ρ€ΡƒΠ΄Π½ΠΎ ΠΏΡ€Π΅Π΄ΡΠΊΠ°Π·Π°Ρ‚ΡŒ, распрСдСлСниС Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ Π² этом пространствС. ЗначСния разбросаны, ΠΈ пространство ΠΎΠ±Ρ‹Ρ‡Π½ΠΎ Ρ…ΠΎΡ€ΠΎΡˆΠΎ визуализируСтся Π² Π΄Π²ΡƒΡ…ΠΌΠ΅Ρ€Π½ΠΎΠΌ прСдставлСнии.

Π­Ρ‚ΠΎ ΠΎΡ‡Π΅Π½ΡŒ полСзная ΠΎΡΠΎΠ±Π΅Π½Π½ΠΎΡΡ‚ΡŒ для систСм сТатия (компрСссии). Однако для Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ Π½ΠΎΠ²Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ знамСнитостСй эта Ρ€Π°Π·Ρ€Π΅ΠΆΠ΅Π½Π½ΠΎΡΡ‚ΡŒ – ΠΏΡ€ΠΎΠ±Π»Π΅ΠΌΠ°, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ Π½Π°ΠΉΡ‚ΠΈ скрытоС Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅, для ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠ³ΠΎ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€ Π±ΡƒΠ΄Π΅Ρ‚ Π·Π½Π°Ρ‚ΡŒ, ΠΊΠ°ΠΊ произвСсти Π½ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½ΠΎΠ΅ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅, ΠΏΠΎΡ‡Ρ‚ΠΈ Π½Π΅Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎ.

Π‘ΠΎΠ»Π΅Π΅ Ρ‚ΠΎΠ³ΠΎ, Ссли Π² пространствС Π΅ΡΡ‚ΡŒ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΊΠΈ ΠΌΠ΅ΠΆΠ΄Ρƒ кластСрами, ΠΈ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€ ΠΏΠΎΠ»ΡƒΡ‡ΠΈΡ‚ Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΡŽ ΠΈΠ· Ρ‚Π°ΠΊΠΎΠ³ΠΎ ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΊΠ°, Π΅ΠΌΡƒ Π½Π΅ Ρ…Π²Π°Ρ‚ΠΈΡ‚ Π·Π½Π°Π½ΠΈΠΉ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΡΠ³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Ρ‡Ρ‚ΠΎ-Π½ΠΈΠ±ΡƒΠ΄ΡŒ ΠΏΠΎΠ»Π΅Π·Π½ΠΎΠ΅.

Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹ΠΉ автоэнкодСр Π΄Π΅Π»Π°Π΅Ρ‚ Π²Π½ΡƒΡ‚Ρ€Π΅Π½Π½Π΅Π΅ пространство Π±ΠΎΠ»Π΅Π΅ прСдсказуСмым, Π±ΠΎΠ»Π΅Π΅ Π½Π΅ΠΏΡ€Π΅Ρ€Ρ‹Π²Π½Ρ‹ΠΌ ΠΈ ΠΌΠ΅Π½Π΅Π΅ Ρ€Π°Π·Ρ€Π΅ΠΆΠ΅Π½Π½Ρ‹ΠΌ. Заставляя скрытыС ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΠΎΠ²Π°Ρ‚ΡŒ Π½ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½ΠΎΠΌΡƒ Ρ€Π°ΡΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΡŽ, VAE ΠΏΠΎΠ»ΡƒΡ‡Π°ΡŽΡ‚ ΠΊΠΎΠ½Ρ‚Ρ€ΠΎΠ»ΡŒ Π½Π°Π΄ скрытым пространством.

ΠŸΠ΅Ρ€Π΅Ρ…ΠΎΠ΄ ΠΎΡ‚ AE ΠΊ VAE, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ случайныС ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅
ΠŸΠ΅Ρ€Π΅Ρ…ΠΎΠ΄ ΠΎΡ‚ AE ΠΊ VAE, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ случайныС ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅

ВмСсто прямой ΠΏΠ΅Ρ€Π΅Π΄Π°Ρ‡ΠΈ скрытых Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€Ρƒ, VAE ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡŽΡ‚ ΠΈΡ… для расчСта срСдних Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ ΠΈ стандартных ΠΎΡ‚ΠΊΠ»ΠΎΠ½Π΅Π½ΠΈΠΉ. Π—Π°Ρ‚Π΅ΠΌ Π²Ρ…ΠΎΠ΄ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€Π° собираСтся ΠΈΠ· ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰Π΅Π³ΠΎ Π½ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½ΠΎΠ³ΠΎ распрСдСлСния.

Π’ процСссС обучСния VAE заставляСт это Π½ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½ΠΎΠ΅ распрСдСлСниС Π±Ρ‹Ρ‚ΡŒ ΠΊΠ°ΠΊ ΠΌΠΎΠΆΠ½ΠΎ Π±ΠΎΠ»Π΅Π΅ Π±Π»ΠΈΠ·ΠΊΠΈΠΌ ΠΊ стандартному Π½ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½ΠΎΠΌΡƒ Ρ€Π°ΡΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΡŽ, Π²ΠΊΠ»ΡŽΡ‡Π°Ρ Π² Ρ„ΡƒΠ½ΠΊΡ†ΠΈΡŽ ΠΏΠΎΡ‚Π΅Ρ€ΡŒ расстояниС ΠšΡƒΠ»ΡŒΠ±Π°ΠΊΠ°-Π›Π΅ΠΉΠ±Π»Π΅Ρ€Π°. VAE Π±ΡƒΠ΄Π΅Ρ‚ ΠΈΠ·ΠΌΠ΅Π½ΡΡ‚ΡŒ, ΠΈΠ»ΠΈ ΠΈΡΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚ΡŒ Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΈ Π½Π° гранях, ΠΈ Π½Π΅ случайным ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ, Π° Π² ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½Π½ΠΎΠΌ, ΠΆΠ΅Π»Π°Π΅ΠΌΠΎΠΌ Π½Π°ΠΏΡ€Π°Π²Π»Π΅Π½ΠΈΠΈ.

УсловныС Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры ΠΏΠΎΠ·Π²ΠΎΠ»ΡΡŽΡ‚ ΠΌΠΎΠ΄Π΅Π»ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π²Ρ…ΠΎΠ΄ Π½Π° основС Π½Π΅ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ скрытой ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½ΠΎΠΉ z, Π½ΠΎ ΠΈ Π΄ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎΠΉ ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΠΈ Π²Ρ€ΠΎΠ΄Π΅ ΠΌΠ΅Ρ‚Π°Π΄Π°Π½Π½Ρ‹Ρ… изобраТСния (ΡƒΠ»Ρ‹Π±ΠΊΠ°, ΠΎΡ‡ΠΊΠΈ, Ρ†Π²Π΅Ρ‚ ΠΊΠΎΠΆΠΈ ΠΈ Ρ‚.ΠΏ.)

Π“Π΅Π½Π΅Ρ€Π°Ρ‚ΠΎΡ€ Π΄Π°Π½Π½Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ

Π”Π°Π²Π°ΠΉΡ‚Π΅ создадим (условный) VAE, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ смоТСт ΠΎΠ±ΡƒΡ‡Π°Ρ‚ΡŒΡΡ Π½Π° Π»ΠΈΡ†Π°Ρ… знамСнитостСй. ΠœΡ‹ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΡΠΊΠΈΠΉ эффСктивный ΠΏΠΎ памяти Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΎΡ€ Keras, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΡΠΏΡ€Π°Π²ΠΈΡ‚ΡŒΡΡ с нашим большим Π½Π°Π±ΠΎΡ€ΠΎΠΌ Π΄Π°Π½Π½Ρ‹Ρ… (202599 ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ, ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π½ΠΎ ΠΏΠΎ 10Кб ΠΊΠ°ΠΆΠ΄ΠΎΠ΅). Π•Π³ΠΎ Ρ†Π΅Π»ΡŒ – ΠΏΠΎΠ»ΡƒΡ‡Π°Ρ‚ΡŒ ΠΏΠ°ΠΊΠ΅Ρ‚Ρ‹ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ Π½Π° Π»Π΅Ρ‚Ρƒ Π² процСссС обучСния.

        import numpy as np

class CustomCelebrityFaceGenerator(Sequence):
    # ΠΈΠ½ΠΈΡ†ΠΈΠ°Π»ΠΈΠ·ΠΈΡ€ΡƒΠ΅ΠΌ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΡΠΊΠΈΠΉ Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΎΡ€
    def __init__(self, df, batch_size, target_height, target_width, conditioning_dim=0):
        self.df = df
        self.batch_size = batch_size
        self.target_height = target_height
        self.target_width = target_width
        self.conditioning_dim = conditioning_dim
        
    # пСрСтасуСм Π΄Π°Π½Π½Ρ‹Π΅ послС ΠΊΠ°ΠΆΠ΄ΠΎΠΉ эпохи 
    def on_epoch_end(self):
        self.df = self.df.sample(frac=1)
    
    # Π²Ρ‹Π±Π΅Ρ€Π΅ΠΌ ΠΏΠ°ΠΊΠ΅Ρ‚ Π² Π²ΠΈΠ΄Π΅ Ρ‚Π΅Π½Π·ΠΎΡ€Π°
    def __getitem__(self, index):
        cur_files = self.df.iloc[index*self.batch_size:(index+1)*self.batch_size]
        X, y = self.__data_generation(cur_files)
        return X, y
    
    # 
    def __data_generation(self, cur_files):
        # ΠΈΠ½ΠΈΡ†ΠΈΠ°Π»ΠΈΠ·ΠΈΡ€ΡƒΠ΅ΠΌ пустыС Ρ‚Π΅Π½Π·ΠΎΡ€Ρ‹ для хранСния ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ  
        X = np.empty(shape=(self.batch_size, self.target_height, self.target_width, 3))
        Y = np.empty(shape=(self.batch_size, self.target_height, self.target_width, 3))
        # ΠΈΠ½ΠΈΡ†ΠΈΠ°Π»ΠΈΠ·ΠΈΡ€ΡƒΠ΅ΠΌ пустой Ρ‚Π΅Π½Π·ΠΎΡ€ для хранСния условных ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ…
        if self.conditioning_dim > 0:
            C = np.empty(shape=(self.batch_size, self.conditioning_dim))
        
        # ΠΏΡ€ΠΎΡ…ΠΎΠ΄ΠΈΠΌ Ρ†ΠΈΠΊΠ»ΠΎΠΌ ΠΏΠΎ Ρ‚Π΅ΠΊΡƒΡ‰Π΅ΠΌΡƒ ΠΏΠ°ΠΊΠ΅Ρ‚Ρƒ ΠΈ создаСм Ρ‚Π΅Π½Π·ΠΎΡ€Ρ‹ 
        for i in range(0, self.batch_size):
            # Ρ‡ΠΈΡ‚Π°Π΅ΠΌ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅
            file = cur_files.iloc[i]
            img_uri = 'img_align_celeba/' + file.image_id
            img = skimage.io.imread(img_uri)
            # измСняСм Ρ€Π°Π·ΠΌΠ΅Ρ€Ρ‹ изобраТСния
            if img.shape[0] != self.target_height or img.shape[1] != self.target_width:
                img = skimage.transform.resize(img, (self.target_height, self.target_width)) 
            # сохраняСм ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ Π² Ρ‚Π΅Π½Π·ΠΎΡ€Π°Ρ… 
            img = img.astype(np.float32) / 255.
            X[i] = img
            Y[i] = img
            # сохраняСм условныС ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹ Π² Ρ‚Π΅Π½Π·ΠΎΡ€Π°Ρ…
            if self.conditioning_dim > 0:
                C[i] = list(file[1:file.shape[0]])
            
        if self.conditioning_dim > 0:
            return [X, C], Y
        else:
            return X, Y
    
    # ΠΏΠΎΠ»ΡƒΡ‡ΠΈΡ‚ΡŒ количСство ΠΏΠ°ΠΊΠ΅Ρ‚ΠΎΠ²
    def __len__(self):
        return int(np.floor(self.df.shape[0] / self.batch_size))
    

НСйронная ΡΠ΅Ρ‚ΡŒ VAE

ΠœΡ‹ Ρ…ΠΎΡ‚ΠΈΠΌ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ наш энкодСр Π±Ρ‹Π» свСрточной Π½Π΅ΠΉΡ€ΠΎΠ½Π½ΠΎΠΉ ΡΠ΅Ρ‚ΡŒΡŽ, ΠΏΡ€ΠΈΠ½ΠΈΠΌΠ°ΡŽΡ‰Π΅ΠΉ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ ΠΈ Π²Ρ‹Π΄Π°ΡŽΡ‰Π΅ΠΉ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹ распрСдСлСния Q(z | [x,c]), Π³Π΄Π΅ x – Π²Ρ…ΠΎΠ΄Π½ΠΎΠ΅ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ Π»ΠΈΡ†Π°, c – условная пСрСмСнная (Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚Ρ‹ Π»ΠΈΡ†Π°), Π° z – скрытая пСрСмСнная. Π’ этой ΡΡ‚Π°Ρ‚ΡŒΠ΅ ΠΌΡ‹ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌ ΠΏΡ€ΠΎΡΡ‚ΡƒΡŽ Π°Ρ€Ρ…ΠΈΡ‚Π΅ΠΊΡ‚ΡƒΡ€Ρƒ, ΡΠΎΡΡ‚ΠΎΡΡ‰ΡƒΡŽ ΠΈΠ· Π΄Π²ΡƒΡ… свСрточных слоСв ΠΈ слоя Π³Ρ€ΡƒΠΏΠΏΠΈΡ€ΠΎΠ²ΠΊΠΈ (pooling).

Π”Π΅ΠΊΠΎΠ΄Π΅Ρ€ – это свСрточная нСйронная ΡΠ΅Ρ‚ΡŒ, построСнная ΠΏΠΎ-Π΄Ρ€ΡƒΠ³ΠΎΠΌΡƒ. Π­Ρ‚ΠΎ гСнСративная нСйронная ΡΠ΅Ρ‚ΡŒ, Π²Ρ‹Π΄Π°ΡŽΡ‰Π°Ρ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹ распрСдСлСния похоТСсти P([x,z] | c).

        from keras.layers import Conv2D, MaxPooling2D, UpSampling2D

def get_encoder_network(x, num_filters):  
    x = Conv2D(num_filters, 3, activation='relu', padding='same', kernel_initializer='he_normal')(x)
    x = Conv2D(num_filters, 3, activation='relu', padding='same', kernel_initializer='he_normal')(x)
    x = MaxPooling2D()(x)
    return x

def get_decoder_network(x, num_filters):
    x = UpSampling2D()(x)
    x = Conv2D(num_filters, 3, activation='relu', padding = 'same', kernel_initializer = 'he_normal')(x)
    x = Conv2D(num_filters, 3, activation='relu', padding = 'same', kernel_initializer = 'he_normal')(x)
    return x
    

Π’ΠΎΡ‚ Ρ‚Π°ΠΊ выглядит Π°Ρ€Ρ…ΠΈΡ‚Π΅ΠΊΡ‚ΡƒΡ€Π° всСй сСти VAE:

        from keras.layers import Input, Dense, Reshape, Concatenate, Flatten, Lambda, Reshape
from keras.models import Model
from keras import backend as K
from keras.optimizers import Adam

# функция для создания Π½Π΅ΠΉΡ€ΠΎΠ½Π½ΠΎΠΉ сСти автоэнкодСра 
def get_vae(height, width, batch_size, latent_dim, 
            is_variational=True, conditioning_dim=0,
            start_filters=8, nb_capacity=3, 
            optimizer=Adam(lr=0.001)):
    
    # Π’Π₯ΠžΠ” ##
    
    # создаСм слой для Π²Ρ…ΠΎΠ΄Π½ΠΎΠ³ΠΎ изобраТСния 
    # объСдиняСм ΠΌΠ΅Ρ‚Π°Π΄Π°Π½Π½Ρ‹Π΅ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ 
    inputs = Input((height, width, 3))
    if conditioning_dim > 0:
        condition = Input([conditioning_dim])
        condition_up = Dense(height * width)(condition)
        condition_up = Reshape([height, width, 1])(condition_up)
        inputs_new = Concatenate(axis=3)([inputs, condition_up])
    else:
        inputs_new = inputs
    
    
    # Π­ΠΠšΠžΠ”Π•Π  ##
    
    # создаСм ΠΊΠΎΠ΄ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠ΅ слои 
    # Π΄ΡƒΠ±Π»ΠΈΡ€ΡƒΠ΅ΠΌ ΠΊΠΎΠ΄ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠ΅ слои, увСличивая Ρ„ΠΈΠ»ΡŒΡ‚Ρ€Ρ‹ 
    eblock = get_encoder_network(inputs_new, start_filters)
    for i in range(1, nb_capacity+1):
        eblock = get_encoder_network(eblock, start_filters*(2**i))
        
    # создаСм слой скрытого пространства
    _, *shape_spatial = eblock.get_shape().as_list()
    eblock_flat = Flatten()(eblock)    
    if not is_variational:
        z = Dense(latent_dim)(eblock_flat)
    else:
        # Π²Ρ‹Π±ΠΎΡ€ΠΊΠ° скрытых Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ ΠΈΠ· Π½ΠΎΡ€ΠΌΠ°Π»ΡŒΠ½ΠΎΠ³ΠΎ распрСдСлСния
        def sampling(args):
            z_mean, z_log_sigma = args
            epsilon = K.random_normal(shape=(batch_size, latent_dim), mean=0., stddev=1.)
            return z_mean + K.exp(z_log_sigma) * epsilon
        
        z_mean = Dense(latent_dim)(eblock_flat)
        z_log_sigma = Dense(latent_dim)(eblock_flat)
        z = Lambda(sampling, output_shape=(latent_dim,))([z_mean, z_log_sigma])
    
    if conditioning_dim > 0:
        z_ext = Concatenate()([z, condition])

        
    ## Π”Π•ΠšΠžΠ”Π•Π  ##
    
    # создаСм Π΄Π΅ΠΊΠΎΠ΄ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠ΅ ΡΡ‚Π°Ρ‚ΡŒΠΈ
    inputs_embedding = Input([latent_dim + conditioning_dim])
    embedding = Dense(np.prod(shape_spatial), activation='relu')(inputs_embedding)
    embedding = Reshape(eblock.shape.as_list()[1:])(embedding)
    
    # Π΄ΡƒΠ±Π»ΠΈΡ€ΡƒΠ΅ΠΌ ΠΊΠΎΠ΄ΠΈΡ€ΡƒΡŽΡ‰ΠΈΠ΅ слои, увСличивая Ρ„ΠΈΠ»ΡŒΡ‚Ρ€Ρ‹ 
    dblock = get_decoder_network(embedding, start_filters*(2**nb_capacity))
    for i in range(nb_capacity-1, -1, -1):
        dblock = get_decoder_network(dblock, start_filters*(2**i))
        
    output = Conv2D(3, 1, activation = 'tanh')(dblock)
    
    ## VAE ##
    
    # объСдиняСм энкодСр с Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€ΠΎΠΌ 
    decoder = Model(input = inputs_embedding, output = output)
    if conditioning_dim > 0:
        encoder_with_sampling = Model(input = [inputs, condition], output = z)
        encoder_with_sampling_ext = Model(input = [inputs, condition], output = z_ext)
        vae_out = decoder(encoder_with_sampling_ext([inputs, condition]))
        vae = Model(input = [inputs, condition], output = vae_out)
    else:
        encoder_with_sampling = Model(input = inputs, output = z)
        vae_out = decoder(encoder_with_sampling(inputs))
        vae = Model(input = inputs, output = vae_out)
    
    # опрСдСляСм ΠΏΠΎΡ‚Π΅Ρ€ΠΈ VAE ΠΊΠ°ΠΊ сумму MSE and ΠΏΠΎΡ‚Π΅Ρ€ΡŒ расстояния ΠšΡƒΠ»ΡŒΠ±Π°ΠΊΠ°-Π›Π΅ΠΉΠ±Π»Π΅Ρ€Π°
    def vae_loss(x, x_decoded_mean):
        mse_loss = K.mean(mse(x, x_decoded_mean), axis=(1,2)) * height * width
        kl_loss = - 0.5 * K.mean(1 + z_log_sigma - K.square(z_mean) - K.exp(z_log_sigma), axis=-1)
        return mse_loss + kl_loss
        
    if is_variational:
        vae.compile(loss=vae_loss, optimizer=optimizer)
    else:
        vae.compile(loss='mse', optimizer=optimizer)    
        
    return vae, encoder_with_sampling, decoder

# Π³ΠΈΠΏΠ΅Ρ€ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹
VARIATIONAL = True
HEIGHT = 128 
WIDTH = 128 
BATCH_SIZE = 16 
LATENT_DIM = 16
START_FILTERS = 32 
CAPACITY = 3 
CONDITIONING = True 
OPTIMIZER = Adam(lr=0.01)

vae, encoder, decoder = get_vae(is_variational=VARIATIONAL,
                                   height=HEIGHT, 
                                   width=WIDTH, 
                                   batch_size=BATCH_SIZE, 
                                   latent_dim=LATENT_DIM,
                                   conditioning_dim=df_celeb.shape[1]-1, 
                                   start_filters=START_FILTERS,
                                   nb_capacity=CAPACITY,
                                   optimizer=OPTIMIZER)
    

ΠžΠ±ΡƒΡ‡Π΅Π½ΠΈΠ΅

НиТС прСдставлСн процСсс обучСния ΠΌΠΎΠ΄Π΅Π»Π΅ΠΉ VAE Π½Π° Π½Π°Π±ΠΎΡ€Π΅ Π΄Π°Π½Π½Ρ‹Ρ… celebA. Π­Ρ‚ΠΎΡ‚ ΠΊΠΎΠ΄ выполнялся ΠΎΠΊΠΎΠ»ΠΎ 8 часов Π½Π° инстансС AWS с использованиСм 1 GPU.

        # Π΄Π΅Π»ΠΈΠΌ изобраТСния Π½Π° Ρ‚Ρ€Π΅Π½ΠΈΡ€ΠΎΠ²ΠΎΡ‡Π½Ρ‹ΠΉ Π½Π°Π±ΠΎΡ€ ΠΈ Π½Π°Π±ΠΎΡ€ Π²Π°Π»ΠΈΠ΄Π°Ρ†ΠΈΠΈ
msk = np.random.rand(len(df_celeb)) < 0.5
df_celeb_train = df_celeb[msk]
df_celeb_val = df_celeb[~msk]

# создаСм Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΎΡ€Ρ‹ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ для обучСния
gen = CustomCelebrityFaceGenerator(df_celeb_train, 
                          batch_size=BATCH_SIZE, 
                          target_height=HEIGHT, 
                          target_width=WIDTH, 
                          conditioning_dim=df_celeb.shape[1]-1)

# создаСм Π³Π΅Π½Π΅Ρ€Π°Ρ‚ΠΎΡ€Ρ‹ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ для Π²Π°Π»ΠΈΠ΄Π°Ρ†ΠΈΠΈ
gen_val = CustomCelebrityFaceGenerator(df_celeb_val, 
                          batch_size=BATCH_SIZE, 
                          target_height=HEIGHT, 
                          target_width=WIDTH, 
                          conditioning_dim=df_celeb.shape[1]-1)

# ΠΎΠ±ΡƒΡ‡Π°Π΅ΠΌ Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹ΠΉ автоэнкодСр
vae.fit_generator(gen, verbose=1, epochs=20, validation_data=gen_val)
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π’ΠΈΠ·ΡƒΠ°Π»ΠΈΠ·ΠΈΡ€ΡƒΠ΅ΠΌ скрытыС прСдставлСния

ПослС обучСния ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ Π²Ρ‹Π±Ρ€Π°Ρ‚ΡŒ случайноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ ΠΈΠ· нашСго Π½Π°Π±ΠΎΡ€Π° Π΄Π°Π½Π½Ρ‹Ρ… ΠΈ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ ΠΎΠ±ΡƒΡ‡Π΅Π½Π½Ρ‹ΠΉ энкодСр для создания скрытого прСдставлСния изобраТСния.

        # Π²Ρ‹Π±ΠΈΡ€Π°Π΅ΠΌ случайноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅
sample_img, sample_img_meta = show_sample_image(nb=1)

# функция для кодирования ΠΎΠ΄Π½ΠΎΠ³ΠΎ изобраТСния, Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π°ΡŽΡ‰Π°Ρ Π΅Π³ΠΎ скрытоС прСдставлСниС
def encode_image(img, conditioning, encoder, height, width, batch_size):
    # измСняСм Ρ€Π°Π·ΠΌΠ΅Ρ€Ρ‹ изобраТСния
    if img.shape[0] != height or img.shape[1] != width:
        img = skimage.transform.resize(img, (height, width))
    # заполняСм ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΎΠ½ΠΎ соотвСтствовало Ρ€Π°Π·ΠΌΠ΅Ρ€Ρƒ ΠΏΠ°ΠΊΠ΅Ρ‚Π°
    img_single = np.expand_dims(img, axis=0)
    img_single = img_single.astype(np.float32)
    img_single = np.repeat(img_single, batch_size, axis=0)
    # ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌ энкодСр для вычислСния прСдставлСния Π² скрытом пространствС
    if conditioning is None:
        z = encoder.predict(img_single)
    else:
        z = encoder.predict([img_single, np.repeat(np.expand_dims(conditioning, axis=0), batch_size, axis=0)])
    return z

# Π²Ρ‹Π²ΠΎΠ΄ΠΈΠΌ прСдставлСниС Π² скрытом пространствС, созданноС энкодСром
z = encode_image(sample_img.astype(np.float32) / 255., 
                 np.array(sample_img_meta), 
                 encoder, HEIGHT, WIDTH, BATCH_SIZE)
print('latent sample:\n', z[0])
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ это скрытоС прСдставлСниС, Π²Π΅ΠΊΡ‚ΠΎΡ€ ΠΈΠ· 16 Π΄Π΅ΠΉΡΡ‚Π²ΠΈΡ‚Π΅Π»ΡŒΠ½Ρ‹Ρ… чисСл, ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ Π²ΠΈΠ·ΡƒΠ°Π»ΠΈΠ·ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ, ΠΊΠ°ΠΊ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€ восстановил исходноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅.

        def decode_embedding(z, conditioning, decoder):
    if z.ndim < 2:
        z = np.expand_dims(z, axis=0)
    if conditioning is not None:
        z = np.concatenate((z, np.repeat(np.expand_dims(conditioning, axis=0), z.shape[0], axis=0)), axis=1)
    return decoder.predict(z)

# восстановим исходноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅, ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΡ прСдставлСниС скрытого пространства 
ret = decode_embedding(z, sample_img_meta, decoder)
plt.imshow(ret[0])
plt.show()
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π₯отя рСконструированноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ ΠΈ Ρ€Π°Π·ΠΌΡ‹Ρ‚ΠΎ, ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ Π·Π°ΠΌΠ΅Ρ‚ΠΈΡ‚ΡŒ, Ρ‡Ρ‚ΠΎ ΠΎΠ½ΠΎ ΠΎΡ‡Π΅Π½ΡŒ ΠΏΠΎΡ…ΠΎΠΆΠ΅ Π½Π° исходноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅: ΠΏΠΎΠ», Ρ†Π²Π΅Ρ‚ ΠΎΠ΄Π΅ΠΆΠ΄Ρ‹, волосы, ΡƒΠ»Ρ‹Π±ΠΊΠ°, Ρ†Π²Π΅Ρ‚ ΠΊΠΎΠΆΠΈ.

Π“Π΅Π½Π΅Ρ€ΠΈΡ€ΡƒΠ΅ΠΌ Π½ΠΎΠ²Ρ‹Π΅ Π»ΠΈΡ†Π°

УсловныС VAE ΠΌΠΎΠ³ΡƒΡ‚ ΠΈΠ·ΠΌΠ΅Π½ΡΡ‚ΡŒ скрытоС пространство, Ρ‡Ρ‚ΠΎΠ±Ρ‹ Π³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π½ΠΎΠ²Ρ‹Π΅ Π΄Π°Π½Π½Ρ‹Π΅. А это Π·Π½Π°Ρ‡ΠΈΡ‚, Ρ‡Ρ‚ΠΎ ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ ΡΠ³Π΅Π½Π΅Ρ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ случайноС количСство Π½ΠΎΠ²Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Π΄Π΅ΠΊΠΎΠ΄Π΅Ρ€Π°, опрСдСляя Ρ€Π°Π·Π½Ρ‹Π΅ значСния Π·Π°Π΄Π°Π½Π½Ρ‹Ρ… Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ΠΎΠ².

        def generate_new_images_vae(nb=16, smiling=None, male=None, no_beard=None, attractive=None, 
                        bald=None, chubby=None, eyeglasses=None, young = None):
    sample_training_img, sample_training_img_meta = show_sample_image(nb=1, verbose=False)
    plt.clf();
    f, ax = plt.subplots(2, nb//2, figsize=(20,7));
    for i in range(nb):
        meta=2*np.random.rand(meta_cols.shape[0])-1
        meta[2] = attractive if attractive else meta[2]
        meta[4] = bald if bald else meta[4]
        meta[13] = chubby if chubby else meta[13]
        meta[15] = eyeglasses if eyeglasses else meta[15]
        meta[20] = male if male else meta[20]
        meta[24] = no_beard if no_beard else meta[24]
        meta[31] = smiling if smiling else meta[31]
        meta[39] = young if young else meta[39]
        z1 = np.random.rand(LATENT_DIM, LATENT_DIM)
        ret = decode_embedding(z1, meta, decoder)
        ax[i%2][i//2].imshow(ret[0])
        ax[i%2][i//2].set_title('generated img {}'.format(i))
    ax[0][0].imshow(sample_training_img)
    ax[0][0].set_title('training img')
    
 generate_new_images_vae()
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π₯отя наш Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹ΠΉ автоэнкодСр Π²Ρ‹Π΄Π°Π΅Ρ‚ Ρ€Π°Π·ΠΌΡ‹Ρ‚Ρ‹Π΅ изобраТСния, Π½Π΅ ΠΏΠΎΡ…ΠΎΠΆΠΈΠ΅ Π½Π° рСалистичныС Ρ„ΠΎΡ‚ΠΎΠ³Ρ€Π°Ρ„ΠΈΠΈ, ΠΌΡ‹ ΠΌΠΎΠΆΠ΅ΠΌ Ρ€Π°ΡΠΏΠΎΠ·Π½Π°Ρ‚ΡŒ Π½Π° этих изобраТСниях ΠΏΠΎΠ», Ρ†Π²Π΅Ρ‚ ΠΊΠΎΠΆΠΈ, ΡƒΠ»Ρ‹Π±ΠΊΡƒ, ΠΎΡ‡ΠΊΠΈ ΠΈ Ρ†Π²Π΅Ρ‚ волос людСй, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π½ΠΈΠΊΠΎΠ³Π΄Π° Π½Π΅ сущСствовали.

ΠžΡ‚ ΡƒΠ»Ρ‹Π±ΠΊΠΈ станСт ΠΌΠΈΡ€ свСтлСй

УсловныС VAE ΠΌΠΎΠ³ΡƒΡ‚ ΠΏΡ€ΠΎΠ²ΠΎΠ΄ΠΈΡ‚ΡŒ ΠΈΠ½Ρ‚Π΅Ρ€ΠΏΠΎΠ»ΡΡ†ΠΈΡŽ ΠΌΠ΅ΠΆΠ΄Ρƒ Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚Π°ΠΌΠΈ, Ρ‚ΠΎ Π΅ΡΡ‚ΡŒ ΠΎΠ½ΠΈ способны Π·Π°ΡΡ‚Π°Π²ΠΈΡ‚ΡŒ Π»ΠΈΡ†ΠΎ ΡƒΠ»Ρ‹Π±Π°Ρ‚ΡŒΡΡ ΠΈΠ»ΠΈ Π΄ΠΎΠ±Π°Π²ΠΈΡ‚ΡŒ ΠΎΡ‡ΠΊΠΈ, Ссли ΠΈΡ… Π½Π΅ Π±Ρ‹Π»ΠΎ ΠΏΡ€Π΅ΠΆΠ΄Π΅. БСйчас ΠΌΡ‹ Π²Ρ‹Π±Π΅Ρ€Π΅ΠΌ Π»ΠΈΡ†ΠΎ случайной знамСнитости ΠΈΠ· нашСго Π½Π°Π±ΠΎΡ€Π° Π΄Π°Π½Π½Ρ‹Ρ… ΠΈ Π²ΠΎΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌΡΡ прСимущСством ΠΈΠ·ΠΌΠ΅Π½Π΅Π½ΠΈΠΉ скрытого прСдставлСния, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΏΡ€Π΅Π²Ρ€Π°Ρ‚ΠΈΡ‚ΡŒ ТСнскоС Π»ΠΈΡ†ΠΎ Π² муТскоС. ΠœΡ‹ Ρ‚Π°ΠΊΠΆΠ΅ ΠΈΠ·ΠΌΠ΅Π½ΠΈΠΌ Π»ΠΈΡ†Π°, Π΄ΠΎΠ±Π°Π²ΠΈΠ² Π½Π° Π½ΠΈΡ… ΡƒΠ»Ρ‹Π±ΠΊΡƒ, ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΉ ΠΏΡ€Π΅ΠΆΠ΄Π΅ Ρ‚Π°ΠΌ Π½Π΅ Π±Ρ‹Π»ΠΎ.

        # интСрполяция скрытого пространства, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΈΠ·ΠΌΠ΅Π½ΠΈΡ‚ΡŒ исходноС ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅
def display_manifold(decoder, height, width, base_vec, 
                     bound_x=15, bound_y=15, 
                     axis_x=0, axis_y=1, n=15,
                     desc_x = 'x', desc_y = 'y', 
                     file_out=None):
 
    figure = np.zeros((height * (n if bound_y > 0 else 1), width * (n if bound_x > 0 else 1), 3))
    grid_x = np.linspace(-bound_x, bound_x, n) if bound_x > 0 else [0]
    grid_y = np.linspace(-bound_y, bound_y, n) if bound_y > 0 else [0]
    individual_outputs = []

    for i, yi in enumerate(grid_y):
        for j, xi in enumerate(grid_x):
            z_sample = base_vec.copy()
            z_sample[axis_x] = xi 
            z_sample[axis_y] = yi 

            x_decoded = decoder.predict(np.expand_dims(z_sample, axis=0))
            sample = np.clip(x_decoded[0], 0, 1)
            figure[i * height: (i + 1) * height, j * width: (j + 1) * width] = sample
            individual_outputs.append(sample)

    plt.figure(figsize=(10, 10))
    plt.imshow(figure)
    plt.xlabel(desc_x)
    plt.ylabel(desc_y)
    if file_out is not None:
        plt.savefig(file_out, dpi=200, bbox_inches='tight')
    return figure, individual_outputs

# доступныС Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚Ρ‹
meta_cols = df_celeb.columns[1:].values

# измСняСмыС Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚Ρ‹
dim1 = 'Male'
dim2 = 'Smiling'

# ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅ΠΌΠΎΠ΅ скрытоС пространство 
base_vec = np.array(list(z[0]) + sample_img_meta)

# создаСм измСнСния
rendering, _ = display_manifold(
                                decoder, 
                                HEIGHT, 
                                WIDTH, 
                                base_vec, 
                                bound_x=15, 
                                bound_y=15, 
                                axis_x=LATENT_DIM + np.where(meta_cols==dim1)[0][0], 
                                axis_y=LATENT_DIM + np.where(meta_cols==dim2)[0][0], 
                                n=10,
                                desc_x = dim1,
                                desc_y = dim2,
                                file_out = 'rendering_celeba_' + dim1.lower() + '_' + dim2.lower() + '.png'
                                )
    
πŸ€– Π’Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры (VAE) для Ρ‡Π°ΠΉΠ½ΠΈΠΊΠΎΠ² – пошаговоС руководство

Π—Π°ΠΊΠ»ΡŽΡ‡Π΅Π½ΠΈΠ΅

Π’ этой ΡΡ‚Π°Ρ‚ΡŒΠ΅ ΠΌΡ‹ прСдставили условныС Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹Π΅ автоэнкодСры ΠΈ продСмонстрировали, ΠΊΠ°ΠΊ ΠΈΡ… ΠΌΠΎΠΆΠ½ΠΎ ΠΎΠ±ΡƒΡ‡ΠΈΡ‚ΡŒ Π³Π΅Π½Π΅Ρ€Π°Ρ†ΠΈΠΈ Π½ΠΎΠ²Ρ‹Ρ… Ρ€Π°Π·ΠΌΠ΅Ρ‡Π΅Π½Π½Ρ‹Ρ… Π΄Π°Π½Π½Ρ‹Ρ…. ΠœΡ‹ прСдоставили ΠΊΠΎΠ΄ Π½Π° Python для обучСния VAE Π½Π° Π±ΠΎΠ»ΡŒΡˆΠΈΡ… Π½Π°Π±ΠΎΡ€Π°Ρ… Π΄Π°Π½Π½Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ знамСнитостСй. Π­Ρ‚ΠΎΡ‚ ΠΏΠΎΠ΄Ρ…ΠΎΠ΄ ΠΈ ΠΊΠΎΠ΄ ΠΌΠΎΠΆΠ½ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ ΠΈ для ΠΌΠ½ΠΎΠ³ΠΈΡ… Π΄Ρ€ΡƒΠ³ΠΈΡ… Π·Π°Π΄Π°Ρ‡.

Π“Π΅Π½Π΅Ρ€Π°Ρ‚ΠΈΠ²Π½Ρ‹Π΅ ΡΠΎΡΡ‚ΡΠ·Π°Ρ‚Π΅Π»ΡŒΠ½Ρ‹Π΅ сСти (GAN), ΠΊΠ°ΠΊ ΠΏΡ€Π°Π²ΠΈΠ»ΠΎ, Π²Ρ‹Π΄Π°ΡŽΡ‚ изобраТСния, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ выглядят Π΅Ρ‰Π΅ Π»ΡƒΡ‡ΡˆΠ΅, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ ΠΎΠ½ΠΈ ΠΎΠ±ΡƒΡ‡Π°ΡŽΡ‚ΡΡ Ρ€Π°ΡΠΏΠΎΠ·Π½Π°Π²Π°Ρ‚ΡŒ, Ρ‡Ρ‚ΠΎ люди ΡΡ‡ΠΈΡ‚Π°ΡŽΡ‚ фоторСалистичным, Π° Ρ‡Ρ‚ΠΎ Π½Π΅Ρ‚.

ЭтичСский аспСкт использования Ρ‚Π΅Ρ…Π½ΠΎΠ»ΠΎΠ³ΠΈΠΉ VAE/GAN для создания Ρ„Π΅ΠΉΠΊΠΎΠ²Ρ‹Ρ… ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ, Π²ΠΈΠ΄Π΅ΠΎ ΠΈ новостСй слСдуСт Ρ€Π°ΡΡΠΌΠ°Ρ‚Ρ€ΠΈΠ²Π°Ρ‚ΡŒ ΡΠ΅Ρ€ΡŒΠ΅Π·Π½ΠΎ, ΠΈ ΠΎΠ½ΠΈ Π΄ΠΎΠ»ΠΆΠ½Ρ‹ ΠΏΡ€ΠΈΠΌΠ΅Π½ΡΡ‚ΡŒΡΡ отвСтствСнно.

ΠžΠ³Ρ€ΠΎΠΌΠ½ΠΎΠ΅ спасибо ВинсСнту ΠšΠ°ΡΡΠ΅Ρ€Ρƒ (Vincent Casser) Π·Π° Π΅Π³ΠΎ Π·Π°ΠΌΠ΅Ρ‡Π°Ρ‚Π΅Π»ΡŒΠ½Ρ‹ΠΉ ΠΊΠΎΠ΄, содСрТащий Π±ΠΎΠ»Π΅Π΅ ΠΏΡ€ΠΎΠ΄Π²ΠΈΠ½ΡƒΡ‚Ρ‹ΠΉ ΠΏΠΎΠ΄Ρ…ΠΎΠ΄ ΠΊ Ρ€Π΅Π°Π»ΠΈΠ·Π°Ρ†ΠΈΠΈ свСрточных автоэнкодСров для ΠΎΠ±Ρ€Π°Π±ΠΎΡ‚ΠΊΠΈ ΠΈΠ·ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠΉ, ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½Π½Ρ‹ΠΉ Π² Π΅Π³ΠΎ Π±Π»ΠΎΠ³Π΅. ВинсСнт Ρ€Π°Π·Ρ€Π΅ΡˆΠΈΠ» ΠΌΠ½Π΅ Π°Π΄Π°ΠΏΡ‚ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Π΅Π³ΠΎ ΠΊΠΎΠ΄ VAE для этой ΡΡ‚Π°Ρ‚ΡŒΠΈ. Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ Ρ€Π°Π±ΠΎΡ‚Π°ΡŽΡ‰Π΅Π³ΠΎ VAE с нуля довольно слоТно, Ρ‚Π°ΠΊ Ρ‡Ρ‚ΠΎ Π·Π° ΠΊΠΎΠ΄ слСдуСт Π±Π»Π°Π³ΠΎΠ΄Π°Ρ€ΠΈΡ‚ΡŒ ВинсСнта.

Если Π²Ρ‹ Ρ…ΠΎΡ‚ΠΈΡ‚Π΅ ΡƒΠ·Π½Π°Ρ‚ΡŒ большС ΠΎΠ± автоэнкодСрах, Ρ‡ΠΈΡ‚Π°ΠΉΡ‚Π΅ ΡΡ‚Π°Ρ‚ΡŒΡŽ Π”ΠΆΠΎΠ·Π΅Ρ„Π° Π ΠΎΠΊΠΊΠ° «РазбираСмся с Π²Π°Ρ€ΠΈΠ°Ρ†ΠΈΠΎΠ½Π½Ρ‹ΠΌΠΈ автоэнкодСрами (VAE)Β».
***

Π₯ΠΎΡ‡Ρƒ ΠΎΡΠ²ΠΎΠΈΡ‚ΡŒ Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΡ‹ ΠΈ структуры Π΄Π°Π½Π½Ρ‹Ρ…, Π½ΠΎ слоТно Ρ€Π°Π·ΠΎΠ±Ρ€Π°Ρ‚ΡŒΡΡ ΡΠ°ΠΌΠΎΡΡ‚ΠΎΡΡ‚Π΅Π»ΡŒΠ½ΠΎ. Π§Ρ‚ΠΎ Π΄Π΅Π»Π°Ρ‚ΡŒ?

Алгоритмы ΠΈ структуры Π΄Π°Π½Π½Ρ‹Ρ… Π΄Π΅ΠΉΡΡ‚Π²ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎ нСпростая Ρ‚Π΅ΠΌΠ° для ΡΠ°ΠΌΠΎΡΡ‚ΠΎΡΡ‚Π΅Π»ΡŒΠ½ΠΎΠ³ΠΎ изучСния: Π½Π΅ Ρƒ ΠΊΠΎΠ³ΠΎ ΡΠΏΡ€ΠΎΡΠΈΡ‚ΡŒ ΠΈ Ρ‡Ρ‚ΠΎ-Ρ‚ΠΎ ΡƒΡ‚ΠΎΡ‡Π½ΠΈΡ‚ΡŒ. ΠŸΠΎΡΡ‚ΠΎΠΌΡƒ ΠΌΡ‹ запустили курс «Алгоритмы ΠΈ структуры Π΄Π°Π½Π½Ρ‹Ρ…Β», Π½Π° ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΌ Π² Ρ„ΠΎΡ€ΠΌΠ°Ρ‚Π΅ Π΅ΠΆΠ΅Π½Π΅Π΄Π΅Π»ΡŒΠ½Ρ‹Ρ… Π²Π΅Π±ΠΈΠ½Π°Ρ€ΠΎΠ² Π²Ρ‹:

  • ΠΈΠ·ΡƒΡ‡ΠΈΡ‚Π΅ слСнг, Π½Π° ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΌ говорят всС Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚Ρ‡ΠΈΠΊΠΈ нСзависимо ΠΎΡ‚ языка программирования: язык Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΠΎΠ² ΠΈ структур Π΄Π°Π½Π½Ρ‹Ρ…;
  • Π½Π°ΡƒΡ‡ΠΈΡ‚Π΅ΡΡŒ ΠΏΡ€ΠΈΠΌΠ΅Π½ΡΡ‚ΡŒ Π°Π»Π³ΠΎΡ€ΠΈΡ‚ΠΌΡ‹ ΠΈ структуры Π΄Π°Π½Π½Ρ‹Ρ… ΠΏΡ€ΠΈ Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚ΠΊΠ΅ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌ;
  • ΠΏΠΎΠ΄Π³ΠΎΡ‚ΠΎΠ²ΠΈΡ‚Π΅ΡΡŒ ΠΊ тСхничСскому собСсСдованию ΠΈ ΠΏΡ€ΠΎΠ΄Π²ΠΈΠ½ΡƒΡ‚ΠΎΠΉ Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚ΠΊΠ΅.

ΠšΡƒΡ€Ρ ΠΏΠΎΠ΄Ρ…ΠΎΠ΄ΠΈΡ‚ ΠΊΠ°ΠΊ junior, Ρ‚Π°ΠΊ ΠΈ middle-Ρ€Π°Π·Ρ€Π°Π±ΠΎΡ‚Ρ‡ΠΈΠΊΠ°ΠΌ.

Π˜ΡΡ‚ΠΎΡ‡Π½ΠΈΠΊΠΈ

ΠœΠ•Π ΠžΠŸΠ Π˜Π―Π’Π˜Π―

ΠšΠΎΠΌΠΌΠ΅Π½Ρ‚Π°Ρ€ΠΈΠΈ

Π›Π£Π§Π¨Π˜Π• БВАВЬИ ПО Π’Π•ΠœΠ•