基于PaddlePaddle框架的BP神经网络的鲍鱼年龄的预测
生活随笔
收集整理的這篇文章主要介紹了
基于PaddlePaddle框架的BP神经网络的鲍鱼年龄的预测
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
# 經典的線性回歸模型主要用來預測一些存在著線性關系的數據集?;貧w模型可以理解為:存在一個點集,用一條曲線去擬合它分布的過程。如果擬合曲線是一條直線,則稱為線性回歸。如果是一條二次曲線,則被稱為二次回歸。線性回歸是回歸模型中最簡單的一種。 本教程使用PaddlePaddle建立起一個鮑魚年齡預測模型。
#
# 在線性回歸中:
#
# (1)假設函數是指,用數學的方法描述自變量和因變量之間的關系,它們之間可以是一個線性函數或非線性函數。 在本次線性回顧模型中,我們的假設函數為 Y’= wX+b ,其中,Y’表示模型的預測結果(預測的鮑魚年齡),用來和真實的Y區分。模型要學習的參數即:w,b。
#
# (2)損失函數是指,用數學的方法衡量假設函數預測結果與真實值之間的誤差。這個差距越小預測越準確,而算法的任務就是使這個差距越來越小。 建立模型后,我們需要給模型一個優化目標,使得學到的參數能夠讓預測值Y’盡可能地接近真實值Y。這個實值通常用來反映模型誤差的大小。不同問題場景下采用不同的損失函數。 對于線性模型來講,最常用的損失函數就是均方誤差(Mean Squared Error, MSE)。
#
# (3)優化算法:神經網絡的訓練就是調整權重(參數)使得損失函數值盡可能得小,在訓練過程中,將損失函數值逐漸收斂,得到一組使得神經網絡擬合真實模型的權重(參數)。所以,優化算法的最終目標是找到損失函數的最小值。而這個尋找過程就是不斷地微調變量w和b的值,一步一步地試出這個最小值。 常見的優化算法有隨機梯度下降法(SGD)、Adam算法等等
# # # **Step1.數據準備**
#
# **認識數據:**
#
#
# 數據集共4177行,每行9列
#
# 前8列用來描述鮑魚的各種信息,分別是性別、長度、直徑、高度、總重量、皮重、內臟重量、克重,最后一列為該鮑魚的年齡
#
#
# **數據準備:**
#
# 1.從文件中加載數據
#
# 2.對數據進行歸一化
#
# 3.構造數據集提供器# 讀取文件
import numpy as np
import os
import matplotlib.pyplot as pltdata_X = []
data_Y = []
# 將性別(M:雄性,F:雌性,I:未成年)映射成數字
sex_map = { 'I': 0, 'M': 1, 'F': 2 }
with open ('/home/aistudio/data/data15920/baoyu.txt') as f:for line in f.readlines():line = line.split(',')line[0] = sex_map[line[0]]data_X.append(line[:-1])data_Y.append(line[-1:])
# 轉換為nparray
data_X = np.array(data_X, dtype='float32')
data_Y = np.array(data_Y, dtype='float32')
# 檢查大小
print('data shape', data_X.shape, data_Y.shape)
print('data_x shape[1]', data_X.shape[1])
# 歸一化
for i in range(data_X.shape[1]):_min = np.min(data_X[:,i]) #每一列的最小值_max = np.max(data_X[:,i]) #每一列的最大值data_X[:, i] = (data_X[:, i] - _min) / (_max - _min) #歸一化到0-1之間import paddle
import paddle.fluid as fluid
from sklearn.model_selection import train_test_split
# 分割訓練集、測試集
X_train, X_test, y_train, y_test = train_test_split(data_X, #被劃分的樣本特征集data_Y, #被劃分的樣本標簽test_size=0.2, #測試集占比random_state=0) #隨機數種子,在需要重復試驗的時候,保證得到一組一樣的隨機數
# 自定義reader,每次返回一個樣本數據
def reader_creator(_X, _Y):def reader():for _x, _y in zip(_X, _Y):yield [_x, _y] #返回Iterable對象return reader# 一個minibatch中有16個數據
BATCH_SIZE = 20#定義了用于訓練與驗證的數據提供器。提供器每次讀入一個大小為BATCH_SIZE的數據批次。
#BATCH_SIZE個數據項組成一個mini batch。
train_reader = paddle.batch(reader_creator(X_train, y_train),batch_size=BATCH_SIZE)
test_reader = paddle.batch(reader_creator(X_test, y_test), batch_size=BATCH_SIZE)# # **Step2.網絡配置**
#
# **(1)網絡搭建**:對于線性回歸來講,它就是一個從輸入到輸出的簡單的全連接層。
#
# 對于鮑魚年齡預測數據集,假設鮑魚屬性和年齡之間的關系可以被屬性間的線性組合描述。#定義輸入的形狀和數據類型,張量變量x,表示8維的特征值
x = fluid.layers.data(name='x', shape=[8], dtype='float32')#定義輸出的形狀和數據類型,張量y,表示目標值
y = fluid.layers.data(name='y', shape=[1], dtype='float32')#定義一個簡單的線性網絡,連接輸入和輸出的全連接層
#input:輸入;
#size:該層輸出單元的數目
#act:激活函數
fc2 = fluid.layers.fc(input=x, size=200, bias_attr=True)
drop = fluid.layers.dropout(x=fc2, dropout_prob=0.5)
fc3 = fluid.layers.fc(input=drop, size=800, bias_attr=True, act='relu')
drop = fluid.layers.dropout(x=fc3, dropout_prob=0.5)
fc4 = fluid.layers.fc(input=drop, size=800, bias_attr=True, act='relu')
drop = fluid.layers.dropout(x=fc4, dropout_prob=0.5)
fc5 = fluid.layers.fc(input=drop, size=100, bias_attr=True, act='relu')
y_predict=fluid.layers.fc(input=fc5, size=1, bias_attr=True, act=None)# **(2)定義損失函數**
#
# 此處使用均方差損失函數。
#
# square_error_cost(input,lable):接受輸入預測值和目標值,并返回方差估計,即為(y-y_predict)的平方
cost = fluid.layers.square_error_cost(input=y_predict, label=y) #求方差
avg_cost = fluid.layers.mean(cost) #對方差求平均值,得到平均損失
#克隆main_program得到test_program,使用參數for_test來區分該程序是用來訓練還是用來測試,該api請在optimization之前使用.
test_program = fluid.default_main_program().clone(for_test=True)
# **(3)定義優化函數**# 此處使用的是隨機梯度下降。
optimizer = fluid.optimizer.AdamOptimizer(learning_rate=0.0001)
opts = optimizer.minimize(avg_cost)# 完成上述定義,也就是完成了 fluid.default_main_program 的構建過程,fluid.default_main_program 中承載著神經網絡模型,前向反向計算,以及優化算法對網絡中可學習參數的更新。# **fluid的設計思想:**
# 用戶編寫一段python程序,通過調用 Fluid 提供的算子,向一段 Program 中添加**變量**以及**對變量的操作**(Operators )。
#
# 用戶**只需要描述核心的前向計算**,不需要關心反向計算、分布式下以及異構設備下如何計算。
#
# Fluid 的 Program 的形式上類似一段 C++ 或 Java 程序。
#
# 包含:
#
# 1.本地變量的定義
#
# 2.一系列的operator
#
#
# **用戶完成網絡定義后,一段 Fluid 程序中通常存在 2 段 Program:**
#
# 1.**fluid.default_startup_program**:定義了創建模型參數,輸入輸出,以及模型中可學習參數的初始化等各種操作
#
# default_startup_program 可以由框架自動生成,使用時無需顯示地創建
#
#
# 2.**fluid.default_main_program** :定義了神經網絡模型,前向反向計算,以及優化算法對網絡中可學習參數的更新
#
# 使用Fluid的核心就是構建起 default_main_program# # **Step3.網絡訓練 & Step4.網絡評估**# **(1)創建Executor**
#
# 首先定義運算場所 fluid.CPUPlace()和 fluid.CUDAPlace(0)分別表示運算場所為CPU和GPU
#
# Executor:接收傳入的program,通過run()方法運行program。#use_cuda為False,表示運算場所為CPU;use_cuda為True,表示運算場所為GPU
use_cuda = False
place = fluid.CUDAPlace(0) if use_cuda else fluid.CPUPlace()#創建一個Executor實例exe
exe = fluid.Executor(place) #正式進行網絡訓練前,需先執行參數初始化
exe.run(fluid.default_startup_program())# **(2)定義輸入數據維度**
#
# DataFeeder負責將數據提供器(train_reader,test_reader)返回的數據轉成一種特殊的數據結構,使其可以輸入到Executor中。
#
# feed_list設置向模型輸入的向變量表或者變量表名# In[ ]:# 告知網絡傳入的數據分為兩部分,第一部分是x值,第二部分是y值
feeder = fluid.DataFeeder(place=place, feed_list=[x, y])# **(3)定義繪制訓練過程的損失值變化趨勢的方法draw_train_process**# In[ ]:iter=0;
iters=[]
train_costs=[]def draw_train_process(iters,train_costs):title="training cost"plt.title(title, fontsize=24)plt.xlabel("iter", fontsize=14)plt.ylabel("cost", fontsize=14)plt.plot(iters, train_costs,color='red',label='training cost') plt.grid()plt.show()# **(4)訓練并保存模型**
#
# Executor接收傳入的program,并根據feed map(輸入映射表)和fetch_list(結果獲取表) 向program中添加feed operators(數據輸入算子)和fetch operators(結果獲取算子)。 feed map為該program提供輸入數據。fetch_list提供program訓練結束后用戶預期的變量。
#
# 使用feed方式送入訓練數據,先將reader數據轉換為PaddlePaddle可識別的Tensor數據,傳入執行器進行訓練。
#
# 注:enumerate() 函數用于將一個可遍歷的數據對象(如列表、元組或字符串)組合為一個索引序列,同時列出數據和數據下標# In[ ]:#訓練輪數:所有訓練數據的一個前向傳遞和一個后向傳遞為一輪
EPOCH_NUM=100
#模型保存路徑
model_save_dir = "/home/aistudio/work/fit_a_line.inference.model"for pass_id in range(EPOCH_NUM): #訓練EPOCH_NUM輪# 開始訓練for batch_id, data in enumerate(train_reader()): #遍歷train_reader迭代器train_cost = exe.run(program=fluid.default_main_program(),#運行主程序feed=feeder.feed(data), #喂入一個batch的訓練數據fetch_list=[avg_cost]) #fetch 誤差、準確率,fetch_list中設置要獲取的值if batch_id % 100 == 0:print("Pass:%d, Cost:%0.5f" % (pass_id, train_cost[0])) #每訓練100次,打印一次平均損失值iter=iter+1 iters.append(iter) train_costs.append(train_cost[0])# 開始驗證,并輸出驗證集經過一輪的平均損失test_costs = []for batch_id, data in enumerate(test_reader()): #遍歷test_reader迭代器test_cost= exe.run(program=test_program, #運行測試programfeed=feeder.feed(data), #喂入一個batch的測試數據fetch_list=[avg_cost]) #fetch均方誤差,fetch_list中設置要獲取的值test_costs.append(test_cost[0]) test_cost = (sum(test_costs) / len(test_costs)) #每輪的平均誤差print('Test:%d, Cost:%0.5f' % (pass_id, test_cost)) #打印平均損失#保存模型# 如果保存路徑不存在就創建
if not os.path.exists(model_save_dir):os.makedirs(model_save_dir)
print ('save models to %s' % (model_save_dir))#保存訓練參數到指定路徑中,構建一個專門用預測的program
fluid.io.save_inference_model(model_save_dir, #保存預測model的路徑['x'], #預測需要 feed 的數據[y_predict], #保存預測結果的變量exe) #exe 保存 inference model
#繪制訓練過程,損失隨迭代次數的變化
draw_train_process(iters,train_costs)# # **Step5.模型預測**
# **(1)創建預測用的Executor**# In[ ]:infer_exe = fluid.Executor(place) #創建推測用的executor
inference_scope = fluid.core.Scope() #Scope指定作用域# **(2)可視化真實值與預測值方法定義**
def draw_infer_result(groud_truths,infer_results):title='abalone'plt.title(title, fontsize=24)x = np.arange(1,20) y = xplt.plot(x, y)plt.xlabel('ground truth', fontsize=14)plt.ylabel('infer result', fontsize=14)plt.scatter(groud_truths, infer_results,color='green',label='training cost') plt.grid()plt.show()# **(3)開始預測**
#
# 通過fluid.io.load_inference_model,預測器會從params_dirname中讀取已經訓練好的模型,來對從未遇見過的數據進行預測。with fluid.scope_guard(inference_scope):#修改全局/默認作用域(scope), 運行時中的所有變量都將分配給新的scope。#從指定目錄中加載預測模型[inference_program, #預測用的programfeed_target_names, #一個str列表,它包含需要在預測 Program 中提供數據的變量的名稱。fetch_targets] = fluid.io.load_inference_model(#fetch_targets: 從中可以得到預測結果。model_save_dir, #model_save_dir:模型保存路徑 infer_exe) #infer_exe: 預測用executor#獲取預測數據INFER_BATCH_SIZE=10infer_reader = paddle.batch(reader_creator(X_test, y_test), batch_size=INFER_BATCH_SIZE)#從infer_reader中分割xinfer_data = next(infer_reader())infer_x = np.array([data[0] for data in infer_data]).astype("float32")infer_y= np.array([data[1] for data in infer_data]).astype("float32")results = infer_exe.run(inference_program, #預測模型feed={feed_target_names[0]: np.array(infer_x)}, #喂入要預測的x值fetch_list=fetch_targets) #得到推測結果infer_results=[] #預測值groud_truths=[] #真實值sum_cost=0for i in range(INFER_BATCH_SIZE):infer_result=results[0][i] #經過預測后的值ground_truth=infer_y[i] #真實值infer_results.append(infer_result)groud_truths.append(ground_truth)print("No.%d: infer result is %.2f,ground truth is %.2f" % (i, infer_result,ground_truth))cost=np.power(infer_result-ground_truth,2)sum_cost+=costprint("平均誤差為:",sum_cost/INFER_BATCH_SIZE)draw_infer_result(groud_truths,infer_results)
項目源代碼獲取請點擊這里
總結
以上是生活随笔為你收集整理的基于PaddlePaddle框架的BP神经网络的鲍鱼年龄的预测的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 计算机信息检索 服务方式,计算机信息检索
- 下一篇: 鲍鱼年龄预测