tensorflow 2.0 深度学习(第一部分 part2)

TensorFlow基础


数值类型


张量(标量、向量、矩阵)


索引与切片


维度操作


数学运算

1.exp函数即指数函数:e的x次方的函数
	exp:高等数学里以自然常数e为底的指数函数,等于2.718281828459045
	numpy.exp():返回e的幂次方,e是一个常数为2.718281828459045
	exp(0) = e的0次方 = 1
	exp(1) = e的1次方 = e = 2.718281828459045
 	exp(2) = e的2次方 = 7.38905609893065
 
	>>> import numpy as np
	>>> np.exp(1)
	2.718281828459045
	>>> np.exp(2)
	7.38905609893065

2.log10()、log2()
	#log10:以10为底数的对数,对数是对求幂的逆运算
	#log2:以2为底数的对数,对数是对求幂的逆运算

	>>> import numpy as np
	#log10:以10为底,求10的多少次方为1,即10的0次方为1
	>>> np.log10(1)
	0.0
	#log10:以10为底,求10的多少次方为10,即10的1次方为10
	>>> np.log10(10)
	1.0
	#log10:以10为底,求10的多少次方为100,即10的2次方为100
	>>> np.log10(100)
	2.0
	>>> np.log10(1000)
	3.0

	#log2:以2为底,求2的多少次方为1,即2的0次方为1
	>>> np.log2(1)
	0.0
	#log2:以2为底,求2的多少次方为2,即2的1次方为2
	>>> np.log2(2)
	1.0
	#log2:以2为底,求2的多少次方为4,即2的2次方为4
	>>> np.log2(4)
	2.0
	>>> np.log2(8)
	3.0
	>>> np.log2(16)
	4.0

3.log()
	#log默认以e为底,求e(2.718281828459045)的多少次方为1,即e(2.718281828459045)的0次方为1
	>>> np.log(1)
	0.0
	#log默认以e为底,求e(2.718281828459045)的多少次方为e,即e(2.718281828459045)的1次方为e
	>>> np.log(np.e)
	1.0
	#log默认以e为底,求e(2.718281828459045)的多少次方为10,即e(2.718281828459045)的2.302585092994046次方为10
	>>> np.log(10)
	2.302585092994046
	#log默认以e为底,求e(2.718281828459045)的多少次方为100,即e(2.718281828459045)的4.605170185988092次方为100
	>>> np.log(100)
	4.605170185988092

4.math.log()、math.log2()、math.log10()
	#math.log()、math.log2()、math.log10() 等同于 numpy的log()、log2()、log10()
	>>> import math
	#log默认以e为底,求e(2.718281828459045)的多少次方为1,即e(2.718281828459045)的0次方为1
	>>> math.log(1)
	0.0
	>>> math.log(math.e)
	1.0
	>>> math.log(10)
	2.302585092994046
	>>> math.log(100)
	4.605170185988092

	#log2:以2为底,求2的多少次方为1,即2的0次方为1
	>>> math.log2(1)
	0.0
	>>> math.log2(2)
	1.0
	>>> math.log2(4)
	2.0
	 
	#log10:以10为底,求10的多少次方为1,即10的0次方为1
	>>> math.log10(1)
	0.0
	>>> math.log10(10)
	1.0
	>>> math.log10(100)
	2.0

5.math.log(m,n)	和对应的numpy写法(np.log(m) / np.log(n))
	#math.log(m,n) 表示n为底数,m为真数,即以n为底m的对数

	#4的1次方为4
	>>> math.log(4,4)
	1.0
	#3的1.2618595071429148次方约为4
	>>> math.log(4,3)
	1.2618595071429148
	#2的2次方约为4
	>>> math.log(4,2)
	2.0

	#等同于 math.log(4,4)
	>>> np.log(4) / np.log(4)
	1.0
	#等同于 math.log(4,3)
	>>> np.log(4) / np.log(3)
	1.2618595071429148
	#等同于 math.log(4,2)
	>>> np.log(4) / np.log(2)
	2.0


前向传播

import  tensorflow as tf
from    tensorflow import keras
from    tensorflow.keras import datasets
import  os

os.environ['TF_CPP_MIN_LOG_LEVEL'] = '2'

# x: [60k, 28, 28],
# y: [60k]
(x, y), _ = datasets.mnist.load_data()
# x: [0~255] => [0~1.]
x = tf.convert_to_tensor(x, dtype=tf.float32) / 255. #标准化/归一化
y = tf.convert_to_tensor(y, dtype=tf.int32)

print(x.shape, y.shape, x.dtype, y.dtype)
print(tf.reduce_min(x), tf.reduce_max(x))
print(tf.reduce_min(y), tf.reduce_max(y))
 
train_db = tf.data.Dataset.from_tensor_slices((x,y)).batch(128) #构建批量大小
train_iter = iter(train_db) #获取数据集的遍历对象--生成器
sample = next(train_iter) #next调用生成器第一次遍历的批量大小数据
print('batch:', sample[0].shape, sample[1].shape)
 
# [b, 784] => [b, 256] => [b, 128] => [b, 10]
# [dim_in, dim_out], [dim_out]
w1 = tf.Variable(tf.random.truncated_normal([784, 256], stddev=0.1)) #第一层线性的权重
b1 = tf.Variable(tf.zeros([256])) #第一层线性的偏置
w2 = tf.Variable(tf.random.truncated_normal([256, 128], stddev=0.1)) #第二层线性的权重
b2 = tf.Variable(tf.zeros([128])) #第二层线性的偏置
w3 = tf.Variable(tf.random.truncated_normal([128, 10], stddev=0.1)) #第三层线性的权重
b3 = tf.Variable(tf.zeros([10])) #第三层线性的偏置
lr = 1e-3 #学习率

#epoch定义训练次数
for epoch in range(10): # iterate db for 10
    #每次遍历的是数据集中的一个批量大小的数据
    for step, (x, y) in enumerate(train_db): # for every batch
        # x:[128, 28, 28]
        # y: [128]
        # [b, 28, 28] => [b, 28*28]
        x = tf.reshape(x, [-1, 28*28]) #展平为[批量大小, 28*28]
        #构建梯度记录环境
        with tf.GradientTape() as tape: # tf.Variable
            # x: [b, 28*28]
            # h1 = x@w1 + b1
            # [b, 784]@[784, 256] + [256] => [b, 256] + [256] => [b, 256] + [b, 256]
            h1 = x@w1 + tf.broadcast_to(b1, [x.shape[0], 256]) #第一层线性运算
            h1 = tf.nn.relu(h1) #第一层非线性运算--激活函数
            # [b, 256] => [b, 128]
            h2 = h1@w2 + b2  #第二层线性运算
            h2 = tf.nn.relu(h2) #第二层非线性运算--激活函数
            # [b, 128] => [b, 10] 
            out = h2@w3 + b3 #第三层线性运算

            # compute loss
            # out: [b, 10]
            # y: [b] => [b, 10]
            y_onehot = tf.one_hot(y, depth=10) #真实标签one-hot化

            # mse = mean(sum(y-out)^2)  均方差:计算每个样本的平均误差,再把总误差除以总样本数
            # [b, 10]
            loss = tf.square(y_onehot - out)
            # mean: scalar
            loss = tf.reduce_mean(loss)

        #1.求导,tape.gradient(y,[参数θ])求参数θ相对于y的梯度信息
        #  dy_dw = tape.gradient(y, [w])
        #2.通过tape.gradient(loss,[参数θ])函数求得网络参数θ的梯度信息
        #  grads = tape.gradient(loss, [w1, b1, w2, b2, w3, b3]) 
        #  根据loss对模型所有参数求导 tape.gradient(loss, model.trainable_variables)
        # Step3. optimize and update w1, w2, w3, b1, b2, b3
        # 根据loss 求w1, w2, w3, b1, b2, b3的梯度值 用于后面继续更新对应的模型参数θ
        # compute gradients
        grads = tape.gradient(loss, [w1, b1, w2, b2, w3, b3])
        # print(grads)

        #优化器规则,根据 模型参数θ = θ - lr * grad 更新网络参数
        # w1 = w1 - lr * w1_grad
        w1.assign_sub(lr * grads[0])
        b1.assign_sub(lr * grads[1])
        w2.assign_sub(lr * grads[2])
        b2.assign_sub(lr * grads[3])
        w3.assign_sub(lr * grads[4])
        b3.assign_sub(lr * grads[5])

        if step % 100 == 0:
            print(epoch, step, 'loss:', float(loss))

发布了225 篇原创文章 · 获赞 111 · 访问量 16万+

猜你喜欢

转载自blog.csdn.net/zimiao552147572/article/details/104086557