Merge branch 'master' into advanced_logging
This commit is contained in:
20 files changed
+481
-297
No files matched your search
@@ -4,10 +4,12 @@ import torch.distributed as dist
|
||||
import torch.nn.functional as F
|
||||
import torch.optim as optim
|
||||
import torch.optim.lr_scheduler as lr_scheduler
|
||||
import torch.utils.data
|
||||
from torch.utils.tensorboard import SummaryWriter
|
||||
|
||||
import test # import test.py to get mAP after each epoch
|
||||
from models.yolo import Model
|
||||
from utils import google_utils
|
||||
from utils.datasets import *
|
||||
from utils.utils import *
|
||||
|
||||
@@ -72,6 +74,7 @@ def train(hyp):
|
||||
# Create model
|
||||
model = Model(opt.cfg).to(device)
|
||||
assert model.md['nc'] == nc, '%s nc=%g classes but %s nc=%g classes' % (opt.data, nc, opt.cfg, model.md['nc'])
|
||||
model.names = data_dict['names']
|
||||
|
||||
# Image sizes
|
||||
gs = int(max(model.stride)) # grid size (max stride)
|
||||
@@ -148,37 +151,17 @@ def train(hyp):
|
||||
world_size=1, # number of nodes
|
||||
rank=0) # node rank
|
||||
model = torch.nn.parallel.DistributedDataParallel(model)
|
||||
# pip install torch==1.4.0+cu100 torchvision==0.5.0+cu100 -f https://download.pytorch.org/whl/torch_stable.html
|
||||
|
||||
# Dataset
|
||||
dataset = LoadImagesAndLabels(train_path, imgsz, batch_size,
|
||||
augment=True,
|
||||
hyp=hyp, # augmentation hyperparameters
|
||||
rect=opt.rect, # rectangular training
|
||||
cache_images=opt.cache_images,
|
||||
single_cls=opt.single_cls)
|
||||
# Trainloader
|
||||
dataloader, dataset = create_dataloader(train_path, imgsz, batch_size, gs, opt,
|
||||
hyp=hyp, augment=True, cache=opt.cache_images, rect=opt.rect)
|
||||
mlc = np.concatenate(dataset.labels, 0)[:, 0].max() # max label class
|
||||
assert mlc < nc, 'Label class %g exceeds nc=%g in %s. Correct your labels or your model.' % (mlc, nc, opt.cfg)
|
||||
|
||||
# Dataloader
|
||||
batch_size = min(batch_size, len(dataset))
|
||||
nw = min([os.cpu_count(), batch_size if batch_size > 1 else 0, 8]) # number of workers
|
||||
dataloader = torch.utils.data.DataLoader(dataset,
|
||||
batch_size=batch_size,
|
||||
num_workers=nw,
|
||||
shuffle=not opt.rect, # Shuffle=True unless rectangular training is used
|
||||
pin_memory=True,
|
||||
collate_fn=dataset.collate_fn)
|
||||
|
||||
# Testloader
|
||||
testloader = torch.utils.data.DataLoader(LoadImagesAndLabels(test_path, imgsz_test, batch_size,
|
||||
hyp=hyp,
|
||||
rect=True,
|
||||
cache_images=opt.cache_images,
|
||||
single_cls=opt.single_cls),
|
||||
batch_size=batch_size,
|
||||
num_workers=nw,
|
||||
pin_memory=True,
|
||||
collate_fn=dataset.collate_fn)
|
||||
testloader = create_dataloader(test_path, imgsz_test, batch_size, gs, opt,
|
||||
hyp=hyp, augment=False, cache=opt.cache_images, rect=True)[0]
|
||||
|
||||
# Model parameters
|
||||
hyp['cls'] *= nc / 80. # scale coco-tuned hyp['cls'] to current dataset
|
||||
@@ -186,7 +169,6 @@ def train(hyp):
|
||||
model.hyp = hyp # attach hyperparameters to model
|
||||
model.gr = 1.0 # giou loss ratio (obj_loss = 1.0 or giou)
|
||||
model.class_weights = labels_to_class_weights(dataset.labels, nc).to(device) # attach class weights
|
||||
model.names = data_dict['names']
|
||||
|
||||
#save hyperparamter and training options in run folder
|
||||
with open(os.path.join(log_dir, 'hyp.yaml'), 'w') as f:
|
||||
@@ -200,11 +182,17 @@ def train(hyp):
|
||||
c = torch.tensor(labels[:, 0]) # classes
|
||||
# cf = torch.bincount(c.long(), minlength=nc) + 1.
|
||||
# model._initialize_biases(cf.to(device))
|
||||
|
||||
#always plot labels to log_dir
|
||||
plot_labels(labels, save_dir=log_dir)
|
||||
tb_writer.add_histogram('classes', c, 0)
|
||||
|
||||
if tb_writer:
|
||||
tb_writer.add_histogram('classes', c, 0)
|
||||
|
||||
|
||||
# Check anchors
|
||||
check_best_possible_recall(dataset, anchors=model.model[-1].anchor_grid, thr=hyp['anchor_t'], imgsz=imgsz)
|
||||
if not opt.noautoanchor:
|
||||
check_anchors(dataset, model=model, thr=hyp['anchor_t'], imgsz=imgsz)
|
||||
|
||||
# Exponential moving average
|
||||
ema = torch_utils.ModelEMA(model)
|
||||
@@ -216,7 +204,7 @@ def train(hyp):
|
||||
maps = np.zeros(nc) # mAP per class
|
||||
results = (0, 0, 0, 0, 0, 0, 0) # 'P', 'R', 'mAP', 'F1', 'val GIoU', 'val Objectness', 'val Classification'
|
||||
print('Image sizes %g train, %g test' % (imgsz, imgsz_test))
|
||||
print('Using %g dataloader workers' % nw)
|
||||
print('Using %g dataloader workers' % dataloader.num_workers)
|
||||
print('Starting training for %g epochs...' % epochs)
|
||||
# torch.autograd.set_detect_anomaly(True)
|
||||
for epoch in range(start_epoch, epochs): # epoch ------------------------------------------------------------------
|
||||
@@ -285,10 +273,10 @@ def train(hyp):
|
||||
|
||||
# Plot
|
||||
if ni < 3:
|
||||
f = os.path.join(log_dir, 'train_batch%g.jpg' % i) # filename
|
||||
res = plot_images(images=imgs, targets=targets, paths=paths, fname=f)
|
||||
if tb_writer:
|
||||
tb_writer.add_image(f, res, dataformats='HWC', global_step=epoch)
|
||||
f = os.path.join(log_dir, 'train_batch%g.jpg' % ni) # filename
|
||||
result = plot_images(images=imgs, targets=targets, paths=paths, fname=f)
|
||||
if tb_writer and result is not None:
|
||||
tb_writer.add_image(f, result, dataformats='HWC', global_step=epoch)
|
||||
# tb_writer.add_graph(model, imgs) # add model to tensorboard
|
||||
|
||||
# end batch ------------------------------------------------------------------------------------------------
|
||||
@@ -307,7 +295,6 @@ def train(hyp):
|
||||
model=ema.ema,
|
||||
single_cls=opt.single_cls,
|
||||
dataloader=testloader,
|
||||
fast=epoch < epochs / 2,
|
||||
save_dir=log_dir)
|
||||
|
||||
# Write
|
||||
@@ -362,7 +349,7 @@ def train(hyp):
|
||||
if not opt.evolve:
|
||||
plot_results(save_dir = log_dir) # save as results.png
|
||||
print('%g epochs completed in %.3f hours.\n' % (epoch - start_epoch + 1, (time.time() - t0) / 3600))
|
||||
dist.destroy_process_group() if torch.cuda.device_count() > 1 else None
|
||||
dist.destroy_process_group() if device.type != 'cpu' and torch.cuda.device_count() > 1 else None
|
||||
torch.cuda.empty_cache()
|
||||
return results
|
||||
|
||||
@@ -379,6 +366,7 @@ if __name__ == '__main__':
|
||||
parser.add_argument('--rect', action='store_true', help='rectangular training')
|
||||
parser.add_argument('--nosave', action='store_true', help='only save final checkpoint')
|
||||
parser.add_argument('--notest', action='store_true', help='only test final epoch')
|
||||
parser.add_argument('--noautoanchor', action='store_true', help='disable autoanchor check')
|
||||
parser.add_argument('--evolve', action='store_true', help='evolve hyperparameters')
|
||||
parser.add_argument('--bucket', type=str, default='', help='gsutil bucket')
|
||||
parser.add_argument('--cache-images', action='store_true', help='cache images for faster training')
|
||||
|
||||
Reference in new issue
Block a user