还是得从代码角度看yolov5(1)

train

【参考文章】:又是经典写到一半发现别人写的更好

基础函数

(1)setattr

setattr(opt, k, v)

将给定对象上的命名属性设置为指定值。
等价于opt.k=v

(2)getattr

callback=getattr(loggers, k)

getattr(对象,名称[,默认值])->值
从对象中获取命名属性;getattr(x,‘y’)等价于x.y
当给定默认参数时,当属性未指定时返回该参数
存在如果没有它,则会在这种情况下引发异常。

(3)register_action

callbacks.register_action(k, callback=getattr(loggers, k))

注册器机制的引入是为了使工程的扩展性变得更好。当产品增加某个功能需要增加一些新函数或者类时,它可以保证我们可以复用之前的逻辑。
注册器的相关内容

(4)parse_known_args

opt = parser.parse_known_args()[0] if known else parser.parse_args()

known在def parse_opt(known=False)
parse_known_args()返回的是一个有两个元素的元组,第一个元素是NameSpace,第二个是一个列表。
NameSpace:如果用命令行输入则按照指定的值,否则则使用默认值
列表:将传入的参数以空格为分节符,还没有使用add_argument进行定义的将会以以字符串的形式存放在列表中

关于parse_known_args的解析这篇写的可以的

(4)check_dataset

在yolov5的使用

data_dict = data_dict or check_dataset(data)  # check if None

检查data,实际上是传入yaml文件,将yaml文件内容转化为字典类型进行存放,最终返回的是字典类型
此处的data文件的来源是:

parser.add_argument(‘–data’, type=str, default=ROOT / ‘data/coco128.yaml’, help=‘dataset.yaml path’)

格式上的问题

(1)if-else格式

才识浅陋第一次看见这种结构记录一下

nc = 1 if single_cls else int(data_dict['nc'])

定义了single_cls(bool)则nc=1否则是int(data_dict[‘nc’])

(2)分布式训练

一般不做分布式训练因此我觉得只要了解这个概念就行

RANK == -1:single-GPU only

LOCAL_RANK = int(os.getenv('LOCAL_RANK', -1))  # https://pytorch.org/docs/stable/elastic/run.html
RANK = int(os.getenv('RANK', -1))
WORLD_SIZE = int(os.getenv('WORLD_SIZE', 1))

world_size:全局进程个数。
rank:表示进程序号,用于进程间通信,可以用于表示进程的优先级。我们一般设置 rank=0 的主机为 master 节点。
local_rank:进程内 GPU 编号,非显式参数,由 torch.distributed.launch 内部指定。比方说, rank=3,local_rank=0 表示第 3 个进程内的第 1 块 GPU

具体定义了这几个变量含义
包括后面的DDP mode都是自定义相关的内容

自定义main函数

(1) Resume

resume通过if和else分为两个部分,if部分是判断是否断点恢复训练

# Resume
  if opt.resume and not check_wandb_resume(opt) and not opt.evolve:  # resume an interrupted run
        ckpt = opt.resume if isinstance(opt.resume, str) else get_latest_run()  # specified or most recent path
        assert os.path.isfile(ckpt), 'ERROR: --resume checkpoint does not exist'
        with open(Path(ckpt).parent.parent / 'opt.yaml', errors='ignore') as f:
            opt = argparse.Namespace(**yaml.safe_load(f))  # replace
        opt.cfg, opt.weights, opt.resume = '', ckpt, True  # reinstate
        LOGGER.info(f'Resuming training from {ckpt}')

else部分:不进行断点恢复(正常训练等情况)都会进入这个分支

else:
    opt.data, opt.cfg, opt.hyp, opt.weights, opt.project = \
        check_file(opt.data), check_yaml(opt.cfg), check_yaml(opt.hyp), str(opt.weights), str(opt.project)  # checks
    assert len(opt.cfg) or len(opt.weights), 'either --cfg or --weights must be specified'
    if opt.evolve:
        if opt.project == str(ROOT / 'runs/train'):  # if default project name, rename to runs/evolve
            opt.project = str(ROOT / 'runs/evolve')
        opt.exist_ok, opt.resume = opt.resume, False  # pass resume to exist_ok and disable resume
    opt.save_dir = str(increment_path(Path(opt.project) / opt.name, exist_ok=opt.exist_ok))

(2)Evolve hyperparameters

parser.add_argument('--evolve', type=int, nargs='?', const=300, help='evolve hyperparameters for x generations')

使用定义好的yaml文件进行超参数进化

超参数进化超参数进化列表,括号里分别为(突变规模, 最小值,最大值)

在这里插入图片描述

(3)select_device

还是提一嘴这个函数,先给在yolov5中的使用

device = select_device(opt.device, batch_size=opt.batch_size)

opt.device实际上我在yaml文件中并没有对这个赋值,所以看了一下函数内部实际上是会自动选择cuda或者是cpu。会将cpu/cuda添加到环境变量中,像这样:

if cpu:
    os.environ['CUDA_VISIBLE_DEVICES'] = '-1'  
    # force torch.cuda.is_available() = False

predict

由于下面会提及我的结构,先给出结构

在这里插入图片描述

解读

FILE = Path(__file__).resolve()
ROOT = FILE.parents[0]  # YOLOv5 root directory
if str(ROOT) not in sys.path:
    sys.path.append(str(ROOT))  # add ROOT to PATH
ROOT = Path(os.path.relpath(ROOT, Path.cwd()))  # relative

首先明确一个观点:__file__表示当前python脚本运行的路径,而且不一定返回绝对路径
(具体内容看这篇blog)

如果当前文件包含在sys.path里面,那么,__file__返回一个相对路径!
如果当前文件不包含在sys.path里面,那么__file__返回一个绝对路径!

以此处为例在我的文件夹中的__file__应该是

D:\computervision\deep_learning_model\yolov5-6.1\detect.py

resolve() :将返回当前工作目录的绝对路径
使路径成为绝对路径,解析途中的所有符号链接,并规范化它(例如在Windows)。

parents返回所有上级(祖先)目录列表,[上级目录, 上上级目录, …, 根目录],祖先是父、祖父、曾祖父,依此类推,一直到根目录为止;
[上级目录, 上上级目录, …, 根目录]依次对应parents[0],parents[1],…

ROOT = FILE.parents[0]得到的路径是 D:\computervision\deep_learning_model\yolov5-6.1

cwd():python中cwd其实就是current work dir 的意思,就是当前工作目录,返回当前工作目录
relpath:把绝对路径转换为相对路径

  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值