深度学习近几年来越来越火热,相信很多人都想加入到这个滚滚洪流当中。但深度学习具体要怎么入门呢,相信很多人还不知道。本节课老shi就带大家了解深度学习到底是什么(期待地搓手手.gif)要入门深度学习,首先得从基础的神经网络学起。感知机就是最简单的神经网络,如下图所示。
神经网络最基本的组成包括输入层、隐藏层、输出层。而每层隐藏层中一般都有相应的神经元和激活函数,神经元用来对输入数据进行相应的运算和处理。激活函数的主要作用是将线性问题转换为非线性问题,进而反馈到输出层得到预测结果。一般来说,仅含有一个隐藏层的神经网络就是我们常说的普通神经网络,当隐藏层比较多(大于2层)的神经网络叫做深度神经网络。深度学习就是使用深层架构(如深度神经网络)的机器学习方法,它可以解决现实中很多复杂的回归和分类问题,所以这也正是深度学习的强大之处。
前面介绍了神经网络的基本组成,有些同学可能对它还是很陌生,接下来我们举个栗子,看看神经网络到底是如何工作的。
前向传播网络
如图所示是一个三层神经网络,两层隐藏层和一层输出层,输入层有两个样本x1和x2,y为网络的输出。
第一层网络的权重为
偏置为
第二层网络的权重为
偏置为
第三层网络的权重为
偏置为
第一个隐藏层计算:
根据图中可得,第一层隐藏层有三个神经元:neu1 、neu2 和neu3 。该层的输入为:
以neu1为例,其输入为:
同理可得
假设f(x)为该层的激活函数,那么该层的输出为: f(z1)、f(z2)和f(z3)
注:同一层激活函数一般相同,不同层之间激活函数可以选择不同。
第二层隐藏层计算:
根据图中可得,第二层隐藏层有两个神经元:neu4 和neu5。该层的输入为:
即第二层的输入是第一层的输出乘以第二层的权重,再加上第二层的偏置。因此得到neu4 和neu5的输入分别为:
该层的输出分别为: f(z4)和f(z5)
输出层计算:
输出层只有一个神经元:neu6 。该层的输入为:
即
假设该网络要解决的是一个二分类问题,那么输出层的激活函数可以使用一个Sigmoid型函数,神经网络最后的输出为:f(z6)
最后我们通过numpy来手动实现一个神经网络实例,以下是实例代码。
——————分割线——————————
# coding:utf8
import numpy as np
# 定义激活函数
def sigmoid(x):
return 1.0/(1+np.exp(-x))
#定义网络
def layer_sizes(X, Y):
n_x = X.shape[0]
n_h = 4
n_y = Y.shape[0]
return (n_x, n_h, n_y)
#初始化参数w/b
def initialize_parameters(n_x, n_h, n_y):
w1 = np.random.randn(n_h, n_x)* 0.01
b1 = np.zeros(n_h ,1)
w2 = np.random.randn(n_y, n_h)* 0.01
b2 = np.zeros((n_y, 1))
assert (w1.shape == (n_h, n_x))
assert (b1.shape == (n_h, 1))
assert (w2.shape == (n_y, n_h))
assert (b2.shape == (n_y, 1))
parameters = {
'w1' : w1,
'b1' : b1,
'w2' : w2,
'b2' : b2
}
return parameters
#前向传播
def forward_propagation(x, parameters):
w1 = parameters['w1']
b1 = parameters['b1']
w2 = parameters['w2']
b2 = parameters['b2']
Z1 = np.dot(w1, x) + b1 #Z1 激活函数之前的线性表达式结果
A1 = np.tanh(Z1) #A1 Z1经过激活函数之后的结果
Z2 = np.dot(w2, Z1) + b2
A2 = sigmoid(Z2)
assert(A2.shape == (1,X.shape[1]))
cache = {'Z1': Z1,
'A1' : A1,
'Z2' : Z2,
'A2' : A2}
return A2, cache
#定义损失函数
def compute_cost(A2, Y, parameters):
m = Y.shape[1]
log_probs = np.multiply(np.log(A2) ,Y) + np.multiply(np.log(1 - A2),1 - Y)
cost = -1/m * np.sum(log_probs) #平均损失
cost = np.squeeze(cost) #从数组的形状中删除单维条目,即把shape中为1的维度去掉
assert(isinstance(cost,float))
return cost