pytorch使用Ray-tune对原有训练模型的代码改写,自动调参(一)
借助Ray-tune
可以对pytorch自动调参,下面就一步步地改写,从原始的训练代码慢慢变为可以自动调参的代码的教程• 保姆级:
文章目录
- 安装依赖
- pytorch模型改写至自动调参
- 步骤1:原有代码要跑通
- 步骤2:修改原有代码
- 步骤3:使用ray的调参代码封装训练代码
安装依赖
pip install -i https://mirrors.aliyun.com/pypi/simple/ 'ray[default]'
注意安装的内容是'ray[default]'
,因为后来的各版本代码有调整,因此统一指定成了这种安装方式,否则代码运行中会有各种warnning。
pytorch模型改写至自动调参
为了增加学习效率,这里举一个没有加任何额外的buff的例子。
这里用随机数生成训练数据,然后随手撘一个三层感知机的模型,运行一下确保跑通即可。
步骤1:原有代码要跑通
假设原有的训练代码如下:
import torch
import torch.nn as nn
import numpy as npclass LinearRegressionModel(nn.Module):def __init__(self, input_shape, linear1, linear2, output_shape):super(LinearRegressionModel, self).__init__()self.linear1 = nn.Linear(input_shape, linear1)self.linear2 = nn.Linear(linear1, linear2)self.linear3 = nn.Linear(linear2, output_shape)def forward(self, x):l1 = self.linear1(x)l2 = self.linear2(l1)l3 = self.linear3(l2)return l3def train_model(x_train, y_train, linear1, linear2):# 指定参数与损失函数model = LinearRegressionModel(x_train.shape[1], linear1, linear2, 1)epochs = 1000 # 迭代1000次learning_rate = 0.01 # 学习率optimizer = torch.optim.SGD(model.parameters(), lr=learning_rate) # 优化函数criterion = nn.MSELoss() # Loss使用MSE值,目标是使MSE最小loss_list = []for epoch in range(epochs):epoch += 1optimizer.zero_grad() # 梯度清零outputs = model(x_train) # 前向传播loss = criterion(outputs, y_train) # 计算损失loss.backward() # 返向传播loss_list.append(loss.detach().numpy())optimizer.step() # 更新权重参数mean_loss = np.mean(loss_list)print("loss: ", mean_loss)if __name__ == '__main__':x_train = torch.randn(100, 4) # 生成100个4维的随机数,作为训练集的 Xy_train = torch.randn(100, 1) # 作为训练集的labeltrain_model(x_train, y_train, 32, 8)
代码一定要跑通无报错哈!要不然会无限报错。
跑通模型后我们得到一个值,可能是loss: 0.6363947
,我们之后的目的是希望找到一组参数linear1 与 linear2
(模型中代表隐层数量),使这个loss
值越小越好!
步骤2:修改原有代码
只需要有如下修改即可:
- 导包
from ray import tune
- 执行依次模型后,返回一个或多个指标,这个指标只能是一个值,作为优化的目标
- 所有的print()操作都要删掉,这个不会影响逻辑,但是会影响控制台的显示效果
一共有3
处修改地点,修改后的代码如下:
import torch
import torch.nn as nn
import numpy as np
from ray import tune # 修改地方1:导包class LinearRegressionModel(nn.Module):def __init__(self, input_shape, linear1, linear2, output_shape):super(LinearRegressionModel, self).__init__()self.linear1 = nn.Linear(input_shape, linear1)self.linear2 = nn.Linear(linear1, linear2)self.linear3 = nn.Linear(linear2, output_shape)def forward(self, x):l1 = self.linear1(x)l2 = self.linear2(l1)l3 = self.linear3(l2)return l3def train_model(x_train, y_train, linear1, linear2):# 指定参数与损失函数model = LinearRegressionModel(x_train.shape[1], linear1, linear2, 1)epochs = 1000 # 迭代1000次learning_rate = 0.01 # 学习率optimizer = torch.optim.SGD(model.parameters(), lr=learning_rate) # 优化函数criterion = nn.MSELoss() # Loss使用MSE值,目标是使MSE最小loss_list = []for epoch in range(epochs):epoch += 1optimizer.zero_grad() # 梯度清零outputs = model(x_train) # 前向传播loss = criterion(outputs, y_train) # 计算损失loss.backward() # 返向传播loss_list.append(loss.detach().numpy())optimizer.step() # 更新权重参数mean_loss = np.mean(loss_list)# print("loss: ", mean_loss) # 修改地方2:不要有任何print()操作影响控制台的观察效果tune.report(my_loss=mean_loss) # 修改地方3:加入tune.report(xxx=value),这里xxx可以自定义if __name__ == '__main__':x_train = torch.randn(100, 4) # 生成100个4维的随机数,作为训练集的 Xy_train = torch.randn(100, 1) # 作为训练集的labeltrain_model(x_train, y_train, 32, 8)
步骤3:使用ray的调参代码封装训练代码
这一步主要是指定调参的参数范围和一些调参规则
步骤如下:
- 修改Model传参的方式,使用
config
替代所有的参数列表 - 把
main
中直接训练模型的代码注释掉,咱们要修改成使用ray启动的方法 - 添加ray的基本配置,进行封装
修改后的代码与注释如下:
import torch
import torch.nn as nn
import numpy as np
from ray import tuneclass LinearRegressionModel(nn.Module):def __init__(self, input_shape, linear1, linear2, output_shape):super(LinearRegressionModel, self).__init__()self.linear1 = nn.Linear(input_shape, linear1)self.linear2 = nn.Linear(linear1, linear2)self.linear3 = nn.Linear(linear2, output_shape)def forward(self, x):l1 = self.linear1(x)l2 = self.linear2(l1)l3 = self.linear3(l2)return l3def train_model(config): # 修改1:修改参数,所有的参数都要借助config传递# 指定参数与损失函数model = LinearRegressionModel(x_train.shape[1], config['linear1'], config['linear2'], 1)epochs = 1000 # 迭代1000次learning_rate = 0.01 # 学习率optimizer = torch.optim.SGD(model.parameters(), lr=learning_rate) # 优化函数criterion = nn.MSELoss() # Loss使用MSE值,目标是使MSE最小loss_list = []for epoch in range(epochs):epoch += 1optimizer.zero_grad() # 梯度清零outputs = model(x_train) # 前向传播loss = criterion(outputs, y_train) # 计算损失loss.backward() # 返向传播loss_list.append(loss.detach().numpy())optimizer.step() # 更新权重参数mean_loss = np.mean(loss_list)tune.report(my_loss=mean_loss)if __name__ == '__main__':x_train = torch.randn(100, 4) # 生成100个4维的随机数,作为训练集的 Xy_train = torch.randn(100, 1) # 作为训练集的label# train_model(x_train, y_train, 32, 8) # 修改2:就不需要这样启动了,注释掉这一行# 修改3:下面就是封装的方法config = {"linear1": tune.sample_from(lambda _: np.random.randint(2, 5)), # 自定义采样"linear2": tune.choice([2, 4, 8, 16]), # 从给定值中随机选择}result = tune.run( # 执行训练过程,执行到这里就会根据config自动调参了train_model, # 要训练的模型resources_per_trial={"cpu": 8, }, # 指定训练资源config=config,num_samples=20, # 迭代的次数)# 得到最后的结果print("======================== Result =========================")print(result.results_df)
跑通后可以得到如下结果:
+-------------------------+------------+-------+-----------+-----------+--------+------------------+-----------+
| Trial name | status | loc | linear1 | linear2 | iter | total time (s) | my_loss |
|-------------------------+------------+-------+-----------+-----------+--------+------------------+-----------|
| train_model_559fb_00000 | TERMINATED | | 2 | 8 | 1 | 0.325345 | 1.05185 |
| train_model_559fb_00001 | TERMINATED | | 3 | 16 | 1 | 0.32275 | 1.06859 |
| train_model_559fb_00002 | TERMINATED | | 4 | 8 | 1 | 0.292687 | 1.04742 |
| train_model_559fb_00003 | TERMINATED | | 2 | 16 | 1 | 0.291877 | 1.06596 |
| train_model_559fb_00004 | TERMINATED | | 3 | 2 | 1 | 0.298721 | 1.04942 |
| train_model_559fb_00005 | TERMINATED | | 4 | 2 | 1 | 0.294107 | 1.06227 |
| train_model_559fb_00006 | TERMINATED | | 2 | 16 | 1 | 0.310592 | 1.04826 |
| train_model_559fb_00007 | TERMINATED | | 4 | 2 | 1 | 0.31578 | 1.0608 |
| train_model_559fb_00008 | TERMINATED | | 3 | 2 | 1 | 0.286066 | 1.05879 |
| train_model_559fb_00009 | TERMINATED | | 3 | 8 | 1 | 0.290412 | 1.05573 |
| train_model_559fb_00010 | TERMINATED | | 2 | 2 | 1 | 0.282055 | 1.04826 |
| train_model_559fb_00011 | TERMINATED | | 4 | 4 | 1 | 0.288696 | 1.05269 |
| train_model_559fb_00012 | TERMINATED | | 2 | 2 | 1 | 0.311075 | 1.06867 |
| train_model_559fb_00013 | TERMINATED | | 3 | 2 | 1 | 0.312876 | 1.06269 |
| train_model_559fb_00014 | TERMINATED | | 3 | 2 | 1 | 0.273914 | 1.06514 |
| train_model_559fb_00015 | TERMINATED | | 4 | 2 | 1 | 0.270813 | 1.05434 |
| train_model_559fb_00016 | TERMINATED | | 4 | 16 | 1 | 0.292606 | 1.06485 |
| train_model_559fb_00017 | TERMINATED | | 3 | 16 | 1 | 0.286667 | 1.05534 |
| train_model_559fb_00018 | TERMINATED | | 4 | 8 | 1 | 0.272169 | 1.06625 |
| train_model_559fb_00019 | TERMINATED | | 2 | 8 | 1 | 0.270342 | 1.0556 |
+-------------------------+------------+-------+-----------+-----------+--------+------------------+-----------+
最后的result.results_df
记录了所有的参数与结果
在结尾处打个断点还能看到可视化的图表:View the Ray dashboard at http://127.0.0.1:8265
,点进连接就可以看到运行状态了,可以通过这个连接拆看运行中的调参程序的运行状态。
程序跑通了就是信心十足,之后会解锁更多调参的内容与技巧
pytorch使用Ray-tune对原有训练模型的代码改写,自动调参(一)相关推荐
- 使用Ray Tune自动调参
文章目录 前言 一.Ray Tune是什么? 二.使用步骤 1.安装包 2.引入库 3.读入数据(与Ray Tune无关) 4.构建神经网络模型(与Ray Tune无关) 5.模型的训练和测试(与Ra ...
- PyTorch + Ray Tune 调参
参考了PyTorch官方文档和Ray Tune官方文档 1.HYPERPARAMETER TUNING WITH RAY TUNE 2.How to use Tune with PyTorch 以Py ...
- Ray.tune可视化调整超参数Tensorflow 2.0
Ray.tune官方文档 调整超参数通常是机器学习工作流程中最昂贵的部分. Tune专为解决此问题而设计,展示了针对此痛点的有效且可扩展的解决方案. 请注意,此示例取决于Tensorflow 2.0. ...
- pytorch 笔记:使用Tune 进行调参
自动进行调参,我们以pytorch笔记:搭建简易CNN_UQI-LIUWJ的博客-CSDN博客的代码为基础,进行output_channel和learning rate的调参 1 导入库 from f ...
- [Ray.Tune]使用心得(待完善)
首先,report中参数,是自行指定的,而参数对应的值需要在程序中有出现,这一点不需要赘述. 同时在report中指定的参数,将会在Ray运行的过程中以表格的形式展现. 比如, tune.report ...
- ray.tune文档总结
ray.tune文档总结 tune.run config指定超参数的搜索方法 ConcurrencyLimiter搜索算法 scheduler试验调度程序 分析 资源(并行.GPU.分布式) 原文档请 ...
- pytorch微调bert_香侬读 | RoBERT: 没错,我就是能更强——更大数据规模和仔细调参下的最优BERT
文章标题:RoBERTa: A Robustly Optimized BERT Pretraining Approach 文章作者:Yinhan Liu, Myle Ott, Naman Goyal, ...
- Pytorch环境下微调BERT以及调参教程
使用Hugginface的Transformers库快速微调BERT等预训练模型,使其适应下游任务,本文以Quora问题对任务为例,对两问题表意是否一致进行预测 介绍 之前写了个微调BERT的入门教程 ...
- Pytorch实现中药材(中草药)分类识别(含训练代码和数据集)
Pytorch实现中药材(中草药)分类识别(含训练代码和数据集) 目录 Pytorch实现中药材(中草药)分类识别(含训练代码和数据集) 1. 前言 2. 中药材(中草药)数据集说明 (1)中药材(中 ...
最新文章
- python函数定义中参数列表里的参数是_详解Python函数中参数带星号是什么意思
- 最常用的10个Matlab快捷键,助你编程更高效
- object dection资源
- php json java_php 解析java传过来的json数据
- Deep learn toolbox:CNN BP求导解析
- 前端工程化系列[03]-Grunt构建工具的运转机制
- C# Select SelectMany 区别
- [2019杭电多校第五场][hdu6630]permutation 2
- struts2框架学习
- 异数OS TCP协议栈测试(一)--数据传输篇
- 安装Sublime Text 3
- 帆软报表多数据集关联合并操作
- [转载]hostapd配置解析
- [分享]高手是怎样炼成的:精妙SQL语句介绍
- sqlserver常用语句(报表,递归,分页等)
- 07 树莓派裸机编程,并在Windows MSYS2 QEMU模拟器中运行
- 电商网站中用户评论模块剖析
- 东南大学计算机考研面试题,东南大学研究生面试经验
- Hyperledger Fabric资产案例-链码实例
- java grizzly_Grizzly简介 | Java Game
热门文章
- 修复漏洞的Istio 1.1.1 发布了
- 日志进程redo thread
- MVC框架中的值提供机制(二)
- WPF之Manipulation
- 多个DataTable的合并成一个新表
- php 实现树状组织图插件,使用jstree插件实现树形结构
- python并行计算进程池通信_Python使用进程池管理进程和进程间通信
- python如何并发上千个get_Python拓展21(python3X之百万并发借鉴)
- tomcat 占用的内存越来越大_智能手机内存为什么越来越大 就这三点原因
- lua游戏开发实践指南光盘_Godot游戏开发实践之一:用High Level Multiplayer API制作多人游戏(上)