当前位置:蜗牛素材网>综合资讯>图文>正文

tensorflow 深度神经网络分类算法 训练深度神经网络拟合正弦函数的详细过程

人气:452 ℃/2023-12-17 07:16:59

采用TensorFlow 实现一个全连接的深度神经往,拟合正弦函数。

正弦函数的公式:y = sin(x)

下******体操作是在本地 Jupyter Notebook 环境中完成的,对Jupyter Notebook 不熟悉的同学,可以参考下面的链接。

1. 需要构建的TensorFlow网络结构

下面要构建的模拟正弦函数的神经网络,包含3个隐藏层,每个隐藏层16个隐藏节点,单变量输入,单变量输出,各层的激活函数都采用 sigmoid函数,需要构建的网络结构如下图所示。

2. 绘制标准的sin曲线

下面实现绘制标准的正弦函数,之后标准的正弦函数和模拟结果都采用 pylab.plot 画到图上,方便做对比。

具体代码:

导入相应的Python包和模块。

import tensorflow as tf

import math

import numpy as np

import matplotlib.pyplot as plt

import pylab

定义draw_sin_line() 函数,该函数用来绘制标准的sin曲线。

def draw_sin_line():

'''

绘制标准的sin曲线

'''

x = np.arange(0, 2*np.pi, 0.01)

x = x.reshape((len(x), 1))

y = np.sin(x)

pylab.plot(x, y, label='标准的sin曲线')

plt.axhline(linewidth=1, color='r')

plt.axvline(x=np.pi, linestyle='--', linewidth=1, color='g')

pylab将所有的功能函数(pyplot状态机函数,大部分是 numpy里面的函数)全部导入其单独的命名空间内。为什么要这样做,是因为这样可以很好地与ipython(或者类似的IDE,比如pycharm)实现很好的交互模式。

上面调用 pylab的plot函数绘制曲线,pylab是python下挺不错的一个画图模块,使用也非常简单。

plt.axhline()函数,绘制平行于x轴的水平参考线。

plt.axvline()函数,绘制平行于y轴的垂直参考线。

3. 创建训练样本

定义 get_train_data() 函数,返回一个训练样本(train_x, train_y),其中 train_x 是随机的自变量,train_y 是train_x 的sin函数值。

具体代码如下:

def get_train_data():

'''

返回一个训练样本(train_x, train_y)

其中 train_x 是随机的自变量,train_y 是train_x 的sin函数值

'''

train_x = np.random.uniform(0.0, 2*np.pi, (1))

train_y = np.sin(train_x)

return train_x, train_y

函数原型: numpy.random.uniform(low,high,size)

功能:从一个均匀分布[low,high)中随机采样,注意定义域是左闭右开,即包含low,不包含high.

参数介绍:

low: 采样下界,float类型,默认值为0;

high: 采样上界,float类型,默认值为1;

size: 输出样本数目,为int或元组(tuple)类型,例如,size=(m,n,k), 则输出m*n*k个样本,缺省时输出1个值。

返回值:ndarray类型,其形状和参数size中描述一致。

4. 定义推理函数inference

构建TensorFlow 网络结构的逻辑在 inference() 函数中实现。

其中,构建了3个隐藏层,每个隐藏层16个节点,连接节点的参数 weight 和 bias的初始化是均值为0、方差为1的随机初始化,每个隐藏层的单位采用 tf.sigmoid() 作为激活函数,输出层中没有增加 sigmoid函数,这是因为前面的几层非线性变换已经提取好了足够充分的特征,使用这些特征已经可以让模型用最后一个线性分类函数来分类。

具体代码如下:

def inference(input_data):

'''

定义前向计算的网络结构

args: 输入x的值,单个值

'''

with tf.variable_scope('hidden1'):

# 第一个隐藏层,采用16个隐藏节点

weights = tf.get_variable("weight", [1, 16], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

biases = tf.get_variable("bias", [1, 16], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

hidden1 = tf.sigmoid(tf.multiply(input_data, weights) biases)

with tf.variable_scope('hidden2'):

# 第二个隐藏层,采用16个隐藏节点

weights = tf.get_varaible("weight", [16, 16], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

biases = tf.get_variable("bias", [16], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

mul = tf.matmul(hidden1, weights)

hidden2 = tf.sigmoid(mul biases)

with tf.variable_scope('hidden3'):

# 第三个隐藏层,采用16个隐藏节点

weights = tf.get_varaible("weight", [16, 16], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

biases = tf.get_variable("bias", [16], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

mul = tf.matmul(hidden2, weights)

hidden3 = tf.sigmoid(mul biases)

with tf.variable_scope('output_layer'):

# 输出层

weights = tf.get_varaible("weight", [16, 1], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

biases = tf.get_variable("bias", [1], tf.float32, initializer=tf.random_normal_initializer(0.0, 1))

output = tf.matmul(hidden3, weights) biases

return output

如果变量存在,函数tf.get_variable( ) 会返回现有的变量。如果变量不存在,会根据给定形状和初始值创建变量。

初始器(initializer)= tf.random_normal_initializer(0.0, 1) 是其中一种内置的初始器。

5. 定义训练函数

使用TensorFlow 实现神经网络时,需要定义网络结构、参数、数据的输入和输出、采用的损失函数和优化方法。

最繁琐的训练中的反向传播、自动求导和参数更新等操作由TensorFlow 负责实现。

具体代码如下,代码中有详细的注释:

# 通过梯度下降将损失最小化

def train():

# 学习率

learning_rate = 0.01

x = tf.placeholder(tf.float32)

y = tf.placeholder(tf.float32)

# 基于训练好的模型推理,获取推理结果

net_out = inference(x)

# 定义损失函数的op

loss_op = tf.square(net_out - y)

# 采用随机梯度下降的优化函数

opt = tf.train.GradientDescentOptimizer(learning_rate)

# 定义训练操作

train_op = opt.minimize(loss_op)

# 变量初始化

init = tf.global_variables_initializer()

with tf.Session() as sess:

# 执行变量的初始化操作

sess.run(init)

print("开始训练 ...")

for i in range(100001):

# 获取训练数据

train_x, train_y = get_train_data()

sess.run(train_op, feed_dict={x: train_x, y: train_y})

# 定时输出当前的状态

if i % 10000 == 0:

times = int(i/10000)

# 每执行10000次训练后,测试一下结果,测试结果用 pylab.plot()函数在界面上绘制出来

test_x_ndarray = np.arange(0, 2 * np.pi, 0.01)

test_y_ndarray = np.zeros([len(test_x_ndarray)])

ind = 0

for test_x in test_x_ndarray:

test_y = sess.run(net_out, feed_dict={x: test_x, y: 1})

# 对数组中指定的索引值指向的元素替换成指定的值

np.put(test_y_ndarray, ind, test_y)

ind = 1

# 先绘制标准的正弦函数的曲线

# 再用虚线绘制出模拟正弦函数的曲线

draw_sin_line()

pylab.plot(test_x_ndarray, test_y_ndarray, '--', label = str(times) ' times')

pylab.legend(loc='upper right')

pylab.show()

print("=== DONE ===")

从输入数据到神经网络,到输出预测值,采用预测值和标准值的差的平方作为损失函数,然后将得到的损失函数的操作 loss_op 传给随机梯度下降优化方法 tf.train.GradientDescentOptimizer,从而得到最后训练操作 train_op。

在会话的run 方法中,传入训练数据,每一次执行 train_op,就会根据输入的训练样本做一次前向计算、一次反向传播和一次参数更新。

每训练10000个样本,就将标准的正弦函数和模拟结果采用 pylab.plot()函数绘制出来做对比,其中用实线表示标准的正弦函数,虚线表示模拟的正弦函数(也就是基于神经网络推理的结果)。

6. 开始验证训练函数

执行 train() 函数,就开始训练并验证。

第一次的参数是随机初始化的,模拟出来的正弦函数和标准的正弦函数完全不一样。

神经网络模型经过训练 10000次之后,测试结果如下。此时,模拟曲线(虚线)开始向实线靠近了。

下面是训练到 10000x10次之后,结果如下。此时,模拟曲线基本上和标准的正弦曲线重合了。

如果觉得拟合度还不够,还可以继续训练。这样,就实现了用深度神经网络模拟正弦函数在0-2Pi的曲线。

参考文章:

《TensorFlow入门与实战》-罗冬日

搜索更多有关“tensorflow 深度神经网络分类算法 训练深度神经网络拟合正弦函数的详细过程”的信息 [百度搜索] [SoGou搜索] [头条搜索] [360搜索]
本网站部分内容、图文来自于网络,如有侵犯您的合法权益,请及时与我们联系,我们将第一时间安排核实及删除!
CopyRight © 2008-2024 蜗牛素材网 All Rights Reserved. 手机版