成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現

發布于 2024-5-20 12:47
瀏覽
0收藏

變分自編碼器是近些年較火的一個生成模型,我個人認為其本質上仍然是一個概率圖模型,只是在此基礎上引入了神經網絡。本文將就變分自編碼器(VAE)進行簡單的原理講解和數學推導。


論文:https://arxiv.org/abs/1312.6114
視頻:https://www.bilibili.com/video/BV1op421S7Ep/

引入

高斯混合模型

生成模型,可以簡單的理解為生成數據 (不 止 , 但 我 們 暫 且 就 這 么 理 解 它) 。假如現在我們有樣本數據,而我們發現這些樣本符合正態分布且樣本具有充分的代表性,因此我們計算出樣本的均值和方差,就能得到樣本的概率分布。然后從正態分布中抽樣,就能得到樣本。這 種 生 成 樣 本 的 過 程 就 是 生 成 過 程 。


可是,假如我們的數據長這樣

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

很顯然,它的數據是由兩個不同的正態分布構成。我們可以計算出這些樣本的概率分布。但是一種更為常見的方法就是將其當作是兩個正態分布。我們引入一個隱變量z。


假 設 z 的 取 值 為 0,1 ,如果z為0,我們就從藍色的概率分布中抽樣;否則為1,則從橙色的概率分布中抽樣。這就是生成過程。


但是這個隱變量z是什么?它其實就是隱藏特征 訓 練 數 據x 的 抽 象 出 來 的 特 征 ,比如,如果x偏小,我們則認為它數據藍色正太分布,否則為橙色。這個 "偏 小" 就是特征,我們把它的取值為0,1(0代表偏小,1代表偏大)。


那這種模型我們如何取訓練它呢?如何去找出這個z呢?一 種 很 直 觀 的 方 法 就 是 重 構 代 價 最 小 ,我們希望,給一個訓練數據x,由x去預測隱變量z,再由隱變量z預測回x,得到的誤差最小。比如假如我們是藍色正態分布,去提取特征z,得到的z再返回來預測x,結果得到的卻是橙色的正態分布,這是不可取的。其模型圖如下

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

這個模型被稱為GMM高斯混合模型

變分自編碼器(VAE)

那它和VAE有什么關聯呢?其實VAE的模型圖跟這個原理差不多。只是有些許改變, 隱 變 量Z 的 維 度 是 連 續 且 高 維 的 , 不 再 是 簡 單 的 離 散 分 布 ,因為假如我們生成的是圖片,我們需要提取出來的特征明顯是要很多的,傳統的GMM無法做到。


VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

也就是將訓練樣本x給神經網絡,讓神經網絡計算出均值和協方差矩陣.


取log 的 原 因 是 傳 統 的 神 經 網 絡 輸 出 值 總 是 有 正 有 負 。有了這兩個值就可以在對應的高斯分布中采樣,得到隱變量z。再讓z經過神經網絡重構回樣本,得到新樣本。這就是整個VAE的大致過程了。


再次強調, 訓 練 過 程 我 們 希 望 每 次 重 構 的 時 候 , 新 樣 本 和 訓 練 樣 本 盡 可 能 的 相 似。


VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區


為什么協方差會變成0?因為采樣具有隨機性,也就是存在噪聲,噪聲是肯定會增加重構的誤差的。神經網絡為了讓誤差最小,是肯定讓這個隨機性越小越好,因為只有這樣,才能重構誤差最小。


但是我們肯定是希望有隨機性的,為什么?因為有隨機性,我們才可以生成不同的樣本??!


VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區


所以,有KL散度去衡量兩個概率分布的相似性

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

KL散度是大于等于0的值,越小則證明越相似

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

所以,我們就是兩個優化目標 ① 最 小 化 重 構 代 價 ② 最 小 化 上 述 的 散 度

依照這兩個條件,建立目標函數,直接梯度下降 其 實 還 需 要 重 參 數 化 , 后 面 會 講 到 ,刷刷刷地往下降,最終收斂。

下面,我們就對其進行簡單的數學推導,并以此推導出目標函數

原理推導

引入目標函數

以VAE的簡略圖為例

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

設我們有N個樣本

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

現在,我們先單獨看看里面某一個樣本的似然,某個樣本記為x

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

所以左邊等于右邊

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

按照上面提到的,我們可以把第一步改成

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

更一般地,我們把它們寫成一起

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

由于KL散度是大于等于0的,所以第①項,就被稱為變分下界。

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

好,現在我們只需要最大化其變分下界(以下省略掉參數)

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

細化目標函數

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

先 來 看 KL 散 度

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

可以分為三部分

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

如果你熟悉高斯分布的高階矩的話,式A和式C完全就是二階原點矩和中心距,是直接可以的得出答案的。

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

當然了,其實我們也可以不對其概率分布進行約束,歸根究底,其讓然是最小重構代價,那么我們的目標函數如果可以充分表達出“最小重構代價”,那么是什么又有何關系呢?

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

可以看到,這就是一個均方差

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

重參數化技巧

有了目標函數,理論上我們直接梯度下降就可以了。然而,別忘了,我們是從中采樣出z來??墒俏覀儏s是用的神經網絡去計算的均值和方差,得到的高斯分布再去采樣,這種情況是不可導的。中間都已經出現了一個斷層了。神經網絡是一層套一層的計算。而采樣計算了一層之后,從這一層中去采樣新的值,再計算下一層。因此,采樣本身是不可導的。

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

代碼實現

VAE變分自編碼器原理解析看這一篇就夠了!另附Python代碼實現-AI.x社區

效果一般,不曉得論文里面用了什么手段,效果看起來比這個好。(這個結果甚至還是我加了一層隱藏層的)

import torch
from torch.utils.data import DataLoader
from torchvision.datasets import MNIST
from torchvision.transforms import transforms
from  torch import nn
from tqdm import tqdm
import matplotlib.pyplot as plt
class VAE(nn.Module):
    def __init__(self,input_dim,hidden_dim,gaussian_dim):
        super().__init__()
        #編碼器
        #隱藏層
        self.fc1=nn.Sequential(
            nn.Linear(in_features=input_dim,out_features=hidden_dim),
            nn.Tanh(),
            nn.Linear(in_features=hidden_dim, out_features=256),
            nn.Tanh(),
        )
        #μ和logσ^2
        self.mu=nn.Linear(in_features=256,out_features=gaussian_dim)
        self.log_sigma=nn.Linear(in_features=256,out_features=gaussian_dim)

        #解碼(重構)
        self.fc2=nn.Sequential(
            nn.Linear(in_features=gaussian_dim,out_features=256),
            nn.Tanh(),
            nn.Linear(in_features=256, out_features=512),
            nn.Tanh(),
            nn.Linear(in_features=512,out_features=input_dim),
            nn.Sigmoid() #圖片被轉為為0,1的值了,故用此函數
        )
    def forward(self,x):
        #隱藏層
        h=self.fc1(x)


        #計算期望和log方差
        mu=self.mu(h)
        log_sigma=self.log_sigma(h)

        #重參數化
        h_sample=self.reparameterization(mu,log_sigma)

        #重構
        recnotallow=self.fc2(h_sample)

        return reconsitution,mu,log_sigma

    def reparameterization(self,mu,log_sigma):
        #重參數化
        sigma=torch.exp(log_sigma*0.5) #計算σ
        e=torch.randn_like(input=sigma,device=device)

        result=mu+e*sigma #依據重參數化技巧可得

        return result
    def predict(self,new_x): #預測
        recnotallow=self.fc2(new_x)

        return reconsitution
def train():

    transformer = transforms.Compose([
        transforms.ToTensor(),
    ]) #歸一化
    data = MNIST("./data", transform=transformer,download=True) #載入數據

    dataloader = DataLoader(data, batch_size=128, shuffle=True) #寫入加載器

    model = VAE(784, 512, 20).to(device) #初始化模型

    optimer = torch.optim.Adam(model.parameters(), lr=1e-3) #初始化優化器

    loss_fn = nn.MSELoss(reductinotallow="sum") #均方差損失
    epochs = 100 #訓練100輪

    for epoch in torch.arange(epochs):
        all_loss = 0
        dataloader_len = len(dataloader.dataset)

        for data in tqdm(dataloader, desc="第{}輪梯度下降".format(epoch)):
            sample, label = data
            sample = sample.to(device)
            sample = sample.reshape(-1, 784) #重塑
            result, mu, log_sigma = model(sample) #預測

            loss_likelihood = loss_fn(sample, result) #計算似然損失

            #計算KL損失
            loss_KL = torch.pow(mu, 2) + torch.exp(log_sigma) - log_sigma - 1

            #總損失
            loss = loss_likelihood + 0.5 * torch.sum(loss_KL)

            #梯度歸0并反向傳播和更新
            optimer.zero_grad()

            loss.backward()

            optimer.step()
            with torch.no_grad():
                all_loss += loss.item()
        print("函數損失為:{}".format(all_loss / dataloader_len))
        torch.save(model, "./model/VAE.pth")
if __name__ == '__main__':
    #是否有閑置GPU
    device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")
    #訓練
    train()

    #載入模型,預測
    model=torch.load("./model/VAE (1).pth",map_locatinotallow="cpu")
    #預測20個樣本
    x=torch.randn(size=(20,20))
    result=model.predict(x).detach().numpy()
    result=result.reshape(-1,28,28)
    #繪圖
    for i in range(20):
        plt.subplot(4,5,i+1)
        plt.imshow(result[i])
        plt.gray()
    plt.show()

VAE有很多的變種優化,感興趣的讀者自行查閱。

結束

以上,就是VAE的原理和推導過程了。能力有限,過程并不嚴謹,如有問題,還望指出。


本文轉自 AI生成未來 ,作者:篝火者2312


原文鏈接:??https://mp.weixin.qq.com/s/LFmFXA1hFZE8lesSk1XzzQ?poc_token=HMnPSmajmz9QXr5QDZlgSltwD4h5noYPraMmDOfv??

已于2024-5-20 12:50:11修改
收藏
回復
舉報
回復
相關推薦
主站蜘蛛池模板: 久草中文在线 | 日韩一二区 | 国产成人在线观看免费 | 国产片侵犯亲女视频播放 | 日本在线小视频 | 亚洲国产精品99久久久久久久久 | 99re在线视频| www.久久国产精品 | 亚洲一区免费视频 | 婷婷色成人| 国产9久| 在线成人av | av一级久久| 亚洲综合色婷婷 | 美女久久 | 黑人久久久 | 91视频官网 | 7777奇米影视 | 欧美lesbianxxxxhd视频社区 | 亚洲五码久久 | 久久久久久黄 | 在线一区视频 | 999国产视频 | 日韩在线综合网 | 欧美视频免费在线观看 | 一区二区三区四区日韩 | 美女人人操 | 欧美a√ | 免费中文字幕 | 精品福利一区二区三区 | 91精品国产乱码久久久 | 一级做a | 日日噜噜噜夜夜爽爽狠狠视频97 | 亚洲成人精品一区 | 日韩高清成人 | 成人一区二区三区在线观看 | 欧美久久国产精品 | 久久久区 | 亚洲狠狠爱一区二区三区 | 日韩一区中文字幕 | 男人的天堂久久 |