摘要:等訓練結束后,輸出層就可以去掉了,因為我們只關心的是從到的變換。需要注意的是,整個網絡的訓練不是一蹴而就的,而是逐層進行的。加入實戰微信群,實戰群,算法微信群,算法群。
作者:chen_h
微信號 & QQ:862251340
微信公眾號:coderpai
簡書地址:https://www.jianshu.com/p/51d...
自編碼器 Autoencoder
稀疏自編碼器 Sparse Autoencoder
降噪自編碼器 Denoising Autoencoder
堆疊自編碼器 Stacked Autoencoder
深度學習的威力在于其能夠逐層地學習原始數據的多種表達方式。每一層都以前一層的表達特征為基礎,抽取出更加抽象,更加適合復雜的特征,然后做一些分類等任務。
堆疊自編碼器(Stacked Autoencoder,SAE)實際上就是做這樣的事情,如前面的自編碼器,稀疏自編碼器和降噪自編碼器都是單個自編碼器,它們通過虛構一個 x -> h -> x 的三層網絡,能過學習出一種特征變化 h = f(wx+b) 。實際上,當訓練結束后,輸出層已經沒有什么意義了,我們一般將其去掉,即將自編碼器表示為:
之前之所以將自編碼器模型表示為3層的神經網絡,那是因為訓練的需要,我們將原始數據作為假想的目標輸出,以此構建監督誤差來訓練整個網絡。等訓練結束后,輸出層就可以去掉了,因為我們只關心的是從 x 到 h 的變換。
接下來的思路就很自然了,我們已經得到特征表達 h ,那么我們可不可以將 h 再作為原始信息,訓練一個新的自編碼器,得到新的特征表達呢?當軟可以,而且這就是所謂的堆疊自編碼器(Stacked Autoencoder,SAE)。Stacked 就是逐層堆疊的意思,這個跟“棧”有點像。當把多個自編碼器 Stack 起來之后,這個系統看起來就像這樣:
這樣就把自編碼器改成了深度結構了,即 learning multiple levels of representation and abstraction (Hinton, Bengio, LeCun, 2015)。需要注意的是,整個網絡的訓練不是一蹴而就的,而是逐層進行的。比如說我們要訓練一個 n -> m -> k 結構的網絡,實際上我們是先訓練網絡 n -> m -> n ,得到 n -> m 的變換,然后再訓練 m -> k -> m 網絡,得到 m -> k 的變換。最終堆疊成 SAE ,即為 n -> m -> k 的結果,整個過程就像一層層往上面蓋房子,這就是大名鼎鼎的 layer-wise unsuperwised pre-training (逐層非監督預訓練)。
接下來我們來看一個具體的例子,假設你想要訓練一個包含兩個隱藏層的堆疊自編碼器,用來訓練 MNIST 手寫數字分類。
首先,你需要用原始輸入 x(k) 訓練第一個稀疏自編碼器中,它能夠學習得到原始輸入的一階特征表示 h(1)(k),如下圖所示:
接著,你需要把原始數據輸入到上述訓練好的稀疏自編碼器中,對于每一個輸入 x(k) ,都可以得到它對應的一階特征表示 h(1)(k) 。然后你再用這些一階特征作為另一個稀疏自編碼器的輸入,使用它們來學習二階特征 h(2)(k) ,如下圖:
同樣,再把一階特征輸入到剛訓練好的第二層稀疏自編碼器中,得到每個 h(1)(k) 對應的二階特征激活值 h(2)(k) 。接下來,你可以把這些二階特征作為 softmax 分類器的輸入,訓練得到一個能將二階特征映射到數字標簽的模型。如下圖:
最終,你可以將這三層結合起來構建一個包含兩個隱藏層和一個最終 softmax 分類器層的堆疊自編碼網絡,這個網絡能夠如你所愿地對 MNIST 數據集進行分類。最終模型如下圖:
實驗代碼如下:
#!/usr/bin/env python # -*- coding: utf-8 -*- import tensorflow as tf import numpy as np import input_data N_INPUT = 28*28 N_HIDDEN_1 = 1000 N_OUTPUT_1 = N_INPUT N_HIDDEN_2 = 1500 N_OUTPUT_2 = N_HIDDEN_1 N_OUTPUT = 10 BATCH_SIZE = 16 0 EPOCHES = 10 RHO = .1 BETA = tf.constant(3.0) LAMBDA = tf.constant(.0001) w_model_one_init = np.sqrt(6. / (N_INPUT + N_HIDDEN_1)) model_one_weights = { "hidden": tf.Variable(tf.random_uniform([N_INPUT, N_HIDDEN_1], minval = -w_model_one_init, maxval = w_model_one_init)), "out": tf.Variable(tf.random_uniform([N_HIDDEN_1, N_OUTPUT_1], minval = -w_model_one_init, maxval = w_model_one_init)) } model_one_bias = { "hidden": tf.Variable(tf.random_uniform([N_HIDDEN_1], minval = -w_model_one_init, maxval = w_model_one_init)), "out": tf.Variable(tf.random_uniform([N_OUTPUT_1], minval = -w_model_one_init, maxval = w_model_one_init)) } w_model_two_init = np.sqrt(6. / (N_HIDDEN_1 + N_HIDDEN_2)) model_two_weights = { "hidden": tf.Variable(tf.random_uniform([N_HIDDEN_1, N_HIDDEN_2], minval = -w_model_two_init, maxval = w_model_two_init)), "out": tf.Variable(tf.random_uniform([N_HIDDEN_2, N_OUTPUT_2], minval = -w_model_two_init, maxval = w_model_two_init)) } model_two_bias = { "hidden": tf.Variable(tf.random_uniform([N_HIDDEN_2], minval = -w_model_two_init, maxval = w_model_two_init)), "out": tf.Variable(tf.random_uniform([N_OUTPUT_2], minval = -w_model_two_init, maxval = w_model_two_init)) } w_model_init = np.sqrt(6. / (N_HIDDEN_2 + N_OUTPUT)) model_weights = { "out": tf.Variable(tf.random_uniform([N_HIDDEN_2, N_OUTPUT], minval = -w_model_init, maxval = w_model_init)) } model_bias = { "out": tf.Variable(tf.random_uniform([N_OUTPUT], minval = -w_model_init, maxval = w_model_init)) } model_one_X = tf.placeholder("float", [None, N_INPUT]) model_two_X = tf.placeholder("float", [None, N_HIDDEN_1]) Y = tf.placeholder("float", [None, N_OUTPUT]) def model_one(X): hidden = tf.sigmoid(tf.add(tf.matmul(X, model_one_weights["hidden"]), model_one_bias["hidden"])) out = tf.sigmoid(tf.add(tf.matmul(hidden, model_one_weights["out"]), model_one_bias["out"])) return [hidden, out] def model_two(X): hidden = tf.sigmoid(tf.add(tf.matmul(X, model_two_weights["hidden"]), model_two_bias["hidden"])) out = tf.sigmoid(tf.add(tf.matmul(hidden, model_two_weights["out"]), model_two_bias["out"])) return [hidden, out] def model(X): hidden_1 = tf.sigmoid(tf.add(tf.matmul(X, model_one_weights["hidden"]), model_one_bias["hidden"])) hidden_2 = tf.sigmoid(tf.add(tf.matmul(hidden_1, model_two_weights["hidden"]), model_two_bias["hidden"])) out = tf.add(tf.matmul(hidden_2, model_weights["out"]), model_bias["out"]) return out def KLD(p, q): invrho = tf.sub(tf.constant(1.), p) invrhohat = tf.sub(tf.constant(1.), q) addrho = tf.add(tf.mul(p, tf.log(tf.div(p, q))), tf.mul(invrho, tf.log(tf.div(invrho, invrhohat)))) return tf.reduce_sum(addrho) mnist = input_data.read_data_sets("MNIST_data/", one_hot=True) trX, trY, teX, teY = mnist.train.images, mnist.train.labels, mnist.test.images, mnist.test.labels # model one model_one_hidden, model_one_out = model_one(model_one_X) # loss model_one_cost_J = tf.reduce_sum(tf.pow(tf.sub(model_one_out, model_one_X), 2)) # cost sparse model_one_rho_hat = tf.div(tf.reduce_sum(model_one_hidden), N_HIDDEN_1) model_one_cost_sparse = tf.mul(BETA, KLD(RHO, model_one_rho_hat)) # cost reg model_one_cost_reg = tf.mul(LAMBDA, tf.add(tf.nn.l2_loss(model_one_weights["hidden"]), tf.nn.l2_loss(model_one_weights["out"]))) # cost function model_one_cost = tf.add(tf.add(model_one_cost_J, model_one_cost_reg), model_one_cost_sparse) train_op_1 = tf.train.AdamOptimizer().minimize(model_one_cost) # ======================================================================================= # model two model_two_hidden, model_two_out = model_two(model_two_X) # loss model_two_cost_J = tf.reduce_sum(tf.pow(tf.sub(model_two_out, model_two_X), 2)) # cost sparse model_two_rho_hat = tf.div(tf.reduce_sum(model_two_hidden), N_HIDDEN_2) model_two_cost_sparse = tf.mul(BETA, KLD(RHO, model_two_rho_hat)) # cost reg model_two_cost_reg = tf.mul(LAMBDA, tf.add(tf.nn.l2_loss(model_two_weights["hidden"]), tf.nn.l2_loss(model_two_weights["out"]))) # cost function model_two_cost = tf.add(tf.add(model_two_cost_J, model_two_cost_reg), model_two_cost_sparse) train_op_2 = tf.train.AdamOptimizer().minimize(model_two_cost) # ======================================================================================= # final model model_out = model(model_one_X) cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(model_out, Y)) train_op = tf.train.RMSPropOptimizer(0.001, 0.9).minimize(cost) predict_op = tf.argmax(model_out, 1) # ======================================================================================= with tf.Session() as sess: init = tf.initialize_all_variables() sess.run(init) for i in xrange(EPOCHES): for start, end in zip(range(0, len(trX), BATCH_SIZE), range(BATCH_SIZE, len(trX), BATCH_SIZE)): input_ = trX[start:end] sess.run(train_op_1, feed_dict = {model_one_X: input_}) print "finish model one ..." for i in xrange(EPOCHES): for start, end in zip(range(0, len(trX), BATCH_SIZE), range(BATCH_SIZE, len(trX), BATCH_SIZE)): input_ = trX[start:end] input_ = sess.run(tf.sigmoid(tf.add(tf.matmul(input_, model_one_weights["hidden"]), model_one_bias["hidden"]))) sess.run(train_op_2, feed_dict = {model_two_X: input_}) print "finish model two ..." for i in xrange(EPOCHES): for start, end in zip(range(0, len(trX), BATCH_SIZE), range(BATCH_SIZE, len(trX), BATCH_SIZE)): input_ = trX[start:end] sess.run(train_op, feed_dict = {model_one_X: input_, Y: trY[start:end]}) print i, np.mean(np.argmax(teY, axis = 1) == sess.run(predict_op, feed_dict = {model_one_X: teX, Y: teY})) print "finish model ..." print np.mean(np.argmax(teY, axis = 1) == sess.run(predict_op, feed_dict = {model_one_X: teX, Y: teY}))
Reference:
UFLDL
知乎
作者:chen_h
微信號 & QQ:862251340
簡書地址:https://www.jianshu.com/p/51d...
CoderPai 是一個專注于算法實戰的平臺,從基礎的算法到人工智能算法都有設計。如果你對算法實戰感興趣,請快快關注我們吧。加入AI實戰微信群,AI實戰QQ群,ACM算法微信群,ACM算法QQ群。長按或者掃描如下二維碼,關注 “CoderPai” 微信號(coderpai)
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/41142.html
摘要:降噪自編碼器認為,設計一個能夠恢復原始信號的自編碼器未必是最好的,而能夠對被污染破壞的原始數據進行編碼解碼,然后還能恢復真正的原始數據,這樣的特征才是好的。該恢復信號盡可能的逼近未被污染的原數據。此時,監督訓練的誤差函數就從原來的變成了。 作者:chen_h微信號 & QQ:862251340微信公眾號:coderpai簡書地址:https://www.jianshu.com/p/f7...
摘要:簡單來說是一個壓縮編碼器,也就是對的一坨東西通過變換,輸出和一樣的東西。例如是一個雞,也是一個雞,是一個鴨,也是一個鴨。學術一點說就是找到一個函數能夠使得,叫做。加入實戰微信群,實戰群,算法微信群,算法群。 作者:chen_h微信號 & QQ:862251340微信公眾號:coderpai簡書地址:https://www.jianshu.com/p/fd3... 自編碼器 Auto...
摘要:稀疏編碼是對網絡的隱藏層的輸出有了約束,即隱藏層神經元輸出的平均值應盡量為。也就是說,大部分的隱藏層神經元都處于非狀態。為了滿足這一條件,隱藏層神經元的活躍度必須接近于。 作者:chen_h微信號 & QQ:862251340微信公眾號:coderpai簡書地址:https://www.jianshu.com/p/5f3... 自編碼器 Autoencoder 稀疏自編碼器 Spa...
摘要:如果你對算法實戰感興趣,請快快關注我們吧。加入實戰微信群,實戰群,算法微信群,算法群。 作者:chen_h微信號 & QQ:862251340微信公眾號:coderpai簡書地址:https://www.jianshu.com/p/b5c... 介紹一些人工智能技術的術語,如果你還有術語補充,請訪問 Github English Terminology 中文術語 neur...
摘要:深度學習通過組合低層特征形成更加抽象的高層表示屬性類別或特征,以發現數據的分布式特征表示。深度學習的概念由等人于年提出。但是自年以來,機器學習領域,取得了突破性的進展。 深度學習是機器學習研究中的一個新的領域,其動機在于建立、模擬人腦進行分析學習的神經網絡,它模仿人腦的機制來解釋數據,例如圖像,聲音和文本。深度學習是無監督學習的一種。 深度學習的概念源于人工神經網絡的研究。含多隱層的多層感知...
閱讀 2183·2021-11-19 09:40
閱讀 1919·2021-11-08 13:24
閱讀 2453·2021-10-18 13:24
閱讀 2858·2021-10-11 10:57
閱讀 3578·2021-09-22 15:42
閱讀 1114·2019-08-29 17:11
閱讀 2528·2019-08-29 16:11
閱讀 2421·2019-08-29 11:11