TensorFlow-2.x-01-从0开始的线性回归

        之前我一直使用的是TensorFlow-1.x的版本,虽说静态图模式比较繁琐,但用习惯了之后还是觉得挺不错的,后来TensorFlow-2.x的版本推出了,听说采用了Keras的高阶API,而且默认使用eager模式,然后我也随便看了一下构建模型的代码,第一感觉是跟Pytorch、mxnet好像,如果学习过这两个DNN框架的朋友们去学TF-2.x的话应该来说比较容易,反正我也不知道到底好不好用,下面我就要像一个小白一样重新开始学习TensorFlow-2.x了(感觉TF-1.x白学了…)。

        先说一下我的机器上的环境,Python-3.6.7、Tensorflow-2.0.2,CUDA-10.0。我在我的机器上配置了两个环境,一个是TF-1.13.1的环境,一个就是虚拟环境TF-2.0.2的环境,并没有使用Anaconda,我用过这东西,可能是我不习惯吧,对它实在是折腾不来,后来通过pip配置了虚拟环境。

        跟mxnet的教程博文一样,本篇章与mxnet一一对应,有些理论部分就不讲解了。

        本章对应的mxnet文章:MXNET深度学习框架-03-采用ndarray和autograd实现线性回归

1、生成数据

tf.random.set_seed(99)
num_inputs = 2
num_examples = 1000
true_w = [2, -3.4] #真实权重
true_b = 4.2 # 真实偏置值
features = tf.random.normal((num_examples, num_inputs),stddev =0.1)
labels = true_w[0] * features[:,0] + true_w[1] * features[:,1] + true_b
labels += tf.random.normal(labels.shape,stddev=0.01)
print(features)

1000个2维数据点的结果:
TensorFlow-2.x-01-从0开始的线性回归_第1张图片
        看起来是不是特简单,直接打印就行了,要在TF-1.X种,还得使用sess.run()方法。

2、绘制散点图查看数据

def set_figsize(figsize=(3.5, 2.5)):
    plt.scatter(features[:, 1], labels, 1) # 第二特征和标签的对应关系
    plt.show()
set_figsize() #调用function显示散点图

结果:
TensorFlow-2.x-01-从0开始的线性回归_第2张图片

3、读取数据

def data_iter(batch_size, features, labels):
    num_examples = len(features)
    indices = list(range(num_examples))
    random.shuffle(indices)
    for i in range(0, num_examples, batch_size):
        j = indices[i: min(i+batch_size, num_examples)]
        yield tf.gather(features, axis=0, indices=j), tf.gather(labels, axis=0, indices=j)
# 取batch数据
for batch_x, batch_y in data_iter(10, features, labels):
    print("特征:",batch_x,"\n","标签:",batch_y)
    break

结果:
TensorFlow-2.x-01-从0开始的线性回归_第3张图片

4、定义模型参数

w = tf.Variable(tf.random.normal((num_inputs, 1), stddev=0.01))
b = tf.Variable(tf.zeros((1,)))

5、定义模型结构

def linreg(X, w, b):
    return tf.matmul(X, w) + b

6、定义损失函数

def squared_loss(y_hat, y):
    return (y_hat - tf.reshape(y, y_hat.shape)) ** 2 /2 #为什么要除以2?好求导

7、定义小批量随机梯度下降-SGD

def sgd(params, lr, batch_size, grads):
    for i, param in enumerate(params):
        param.assign_sub(lr * grads[i] / batch_size)

8、训练模型

lr = 0.03
num_epochs = 50
net = linreg
loss = squared_loss
batch_size=100
for epoch in range(num_epochs):
    train_loss,num_count=0,0
    for X, y in data_iter(batch_size, features, labels):
        num_count+=1  # 取多少次结束
        with tf.GradientTape() as t:
            t.watch([w,b])
            l = loss(net(X, w, b), y)

        grads = t.gradient(l, [w, b])# 通过调用反向函数t.gradients计算小批量随机梯度,并调用优化算法sgd迭代模型参数
        sgd([w, b], lr, batch_size, grads)
    train_loss+=tf.reduce_sum(l).numpy()

    print('epoch %d, loss %f' % (epoch + 1, train_loss/num_count))

结果:
TensorFlow-2.x-01-从0开始的线性回归_第4张图片
9、预测结果:

print(true_w, "",w)
print(true_b, "",b)

结果:
在这里插入图片描述
可以看到,预测的结果已经很接近了。

下面放上所有代码:

import tensorflow as tf
import numpy as np
import matplotlib.pyplot as plt
import random


#1、生成1000个数据
num_inputs = 2
num_examples = 1000
true_w = [2, -3.4] #真实权重
true_b = 4.2 # 真实偏置值
features = tf.random.normal((num_examples, num_inputs),stddev =1)
labels = true_w[0] * features[:,0] + true_w[1] * features[:,1] + true_b
labels += tf.random.normal(labels.shape,stddev=0.01)
# print(features)


#2、绘制散点图查看数据
def set_figsize(figsize=(3.5, 2.5)):
    plt.scatter(features[:, 1], labels, 1) # 第二特征和标签的对应关系
    plt.show()
set_figsize() #调用function显示散点图


#3、读取数据
def data_iter(batch_size, features, labels):
    num_examples = len(features)
    indices = list(range(num_examples))
    random.shuffle(indices)
    for i in range(0, num_examples, batch_size):
        j = indices[i: min(i+batch_size, num_examples)]
        yield tf.gather(features, axis=0, indices=j), tf.gather(labels, axis=0, indices=j)
# 取batch数据
for batch_x, batch_y in data_iter(10, features, labels):
    print("特征:",batch_x,"\n","标签:",batch_y)
    break

#4、定义权重参数
w = tf.Variable(tf.random.normal((num_inputs, 1), stddev=0.01))
b = tf.Variable(tf.zeros((1,)))

#5、定义模型结构
def linreg(X, w, b):
    return tf.matmul(X, w) + b

#6、定义损失函数
def squared_loss(y_hat, y):
    return (y_hat - tf.reshape(y, y_hat.shape)) ** 2 /2 #为什么要除以2?好求导

#7、定义小批量随机梯度下降-SGD
def sgd(params, lr, batch_size, grads):
    for i, param in enumerate(params):
        param.assign_sub(lr * grads[i] / batch_size)

#8、训练
lr = 0.03
num_epochs = 50
net = linreg
loss = squared_loss
batch_size=100
for epoch in range(num_epochs):
    train_loss,num_count=0,0
    for X, y in data_iter(batch_size, features, labels):
        num_count+=1  # 取多少次结束
        with tf.GradientTape() as t:
            t.watch([w,b])
            l = loss(net(X, w, b), y)

        grads = t.gradient(l, [w, b])# 通过调用反向函数t.gradients计算小批量随机梯度,并调用优化算法sgd迭代模型参数
        sgd([w, b], lr, batch_size, grads)
    train_loss+=tf.reduce_sum(l).numpy()

    print('epoch %d, loss %f' % (epoch + 1, train_loss/num_count))
print(true_w, "",w)
print(true_b, "",b)

你可能感兴趣的:(Tensorflow,TensorFlow-2.X,线性回归,深度学习)