def test_class_balance_dataset(self): # Test build dataset = build_dataset( dict( type='ClassBalancedDataset', dataset=self.dataset_cfg, oversample_thr=1., )) assert isinstance(dataset, ClassBalancedDataset) assert dataset.dataset.test_mode == self.dataset_cfg['test_mode'] # Test default_args dataset = build_dataset( dict( type='ClassBalancedDataset', dataset=self.dataset_cfg, oversample_thr=1., ), {'test_mode': True}) assert dataset.dataset.test_mode == self.dataset_cfg['test_mode'] cp_cfg = deepcopy(self.dataset_cfg) cp_cfg.pop('test_mode') dataset = build_dataset( dict( type='ClassBalancedDataset', dataset=cp_cfg, oversample_thr=1., ), {'test_mode': True}) assert dataset.dataset.test_mode
def test_normal_dataset(self): # Test build dataset = build_dataset(self.dataset_cfg) assert isinstance(dataset, ImageNet) assert dataset.test_mode == self.dataset_cfg['test_mode'] # Test default_args dataset = build_dataset(self.dataset_cfg, {'test_mode': True}) assert dataset.test_mode == self.dataset_cfg['test_mode'] cp_cfg = deepcopy(self.dataset_cfg) cp_cfg.pop('test_mode') dataset = build_dataset(cp_cfg, {'test_mode': True}) assert dataset.test_mode
def test_concat_dataset(self): # Test build dataset = build_dataset([self.dataset_cfg, self.dataset_cfg]) assert isinstance(dataset, ConcatDataset) assert dataset.datasets[0].test_mode == self.dataset_cfg['test_mode'] # Test default_args dataset = build_dataset([self.dataset_cfg, self.dataset_cfg], {'test_mode': True}) assert dataset.datasets[0].test_mode == self.dataset_cfg['test_mode'] cp_cfg = deepcopy(self.dataset_cfg) cp_cfg.pop('test_mode') dataset = build_dataset([cp_cfg, cp_cfg], {'test_mode': True}) assert dataset.datasets[0].test_mode
def main(): args = parse_args() outputs = mmcv.load(args.pkl_results) assert 'class_scores' in outputs, \ 'No "class_scores" in result file, please set "--out-items" in test.py' cfg = Config.fromfile(args.config) assert args.metrics, ( 'Please specify at least one metric the argument "--metrics".') if args.cfg_options is not None: cfg.merge_from_dict(args.cfg_options) # import modules from string list. if cfg.get('custom_imports', None): from mmcv.utils import import_modules_from_strings import_modules_from_strings(**cfg['custom_imports']) cfg.data.test.test_mode = True dataset = build_dataset(cfg.data.test) pred_score = outputs['class_scores'] kwargs = {} if args.eval_options is None else args.eval_options eval_kwargs = cfg.get('evaluation', {}).copy() # hard-code way to remove EvalHook args for key in [ 'interval', 'tmpdir', 'start', 'gpu_collect', 'save_best', 'rule' ]: eval_kwargs.pop(key, None) eval_kwargs.update(dict(metric=args.metrics, **kwargs)) print(dataset.evaluate(pred_score, **eval_kwargs))
def test_sample_label(self): train_dataset = build_dataset(self.cfg.data.train) for i in tqdm(range(len(train_dataset))): sample = train_dataset[i] labels = sample["gt_labels"].numpy().tolist() for label in labels: assert 0 <= label <= 66, F"sample index: {i}, labels is: {labels}"
def test_show_train_sample(self): train_dataset = build_dataset(self.cfg.data.train) random_index = random.choice(range(len(train_dataset))) print(F"train random index: {random_index}") random_train_data = train_dataset[random_index] print(F"image shape: {random_train_data['img'].data.shape}") self.show_train_image(random_train_data, "train_sample")
def test_kfold_dataset(self): # Test build dataset = build_dataset( dict( type='KFoldDataset', dataset=self.dataset_cfg, fold=0, num_splits=5, test_mode=False, )) assert isinstance(dataset, KFoldDataset) assert not dataset.test_mode assert dataset.dataset.test_mode == self.dataset_cfg['test_mode'] # Test default_args dataset = build_dataset(dict( type='KFoldDataset', dataset=self.dataset_cfg, fold=0, num_splits=5, test_mode=False, ), default_args={ 'test_mode': True, 'classes': [1, 2, 3] }) assert not dataset.test_mode assert dataset.dataset.test_mode == self.dataset_cfg['test_mode'] assert dataset.dataset.CLASSES == [1, 2, 3] cp_cfg = deepcopy(self.dataset_cfg) cp_cfg.pop('test_mode') dataset = build_dataset(dict( type='KFoldDataset', dataset=self.dataset_cfg, fold=0, num_splits=5, ), default_args={ 'test_mode': True, 'classes': [1, 2, 3] }) # The test_mode in default_args will be passed to KFoldDataset assert dataset.test_mode assert not dataset.dataset.test_mode # Other default_args will be passed to child dataset. assert dataset.dataset.CLASSES == [1, 2, 3]
def main(): args = parse_args() if args.out is not None and not args.out.endswith(('.pkl', '.pickle')): raise ValueError('The output file must be a pkl file.') cfg = mmcv.Config.fromfile(args.config) if args.cfg_options is not None: cfg.merge_from_dict(args.cfg_options) # build dataset and dataloader dataset = build_dataset(cfg.data.test) data_loader = build_dataloader(dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, shuffle=False, round_up=False) # build onnxruntime model and run inference. if args.backend == 'onnxruntime': model = ONNXRuntimeClassifier(args.model, class_names=dataset.CLASSES, device_id=0) elif args.backend == 'tensorrt': model = TensorRTClassifier(args.model, class_names=dataset.CLASSES, device_id=0) else: print('Unknown backend: {}.'.format(args.model)) exit(1) model = MMDataParallel(model, device_ids=[0]) model.CLASSES = dataset.CLASSES outputs = single_gpu_test(model, data_loader, args.show, args.show_dir) if args.metrics: results = dataset.evaluate(outputs, args.metrics, args.metric_options) for k, v in results.items(): print(f'\n{k} : {v:.2f}') else: warnings.warn('Evaluation metrics are not specified.') scores = np.vstack(outputs) pred_score = np.max(scores, axis=1) pred_label = np.argmax(scores, axis=1) pred_class = [dataset.CLASSES[lb] for lb in pred_label] results = { 'pred_score': pred_score, 'pred_label': pred_label, 'pred_class': pred_class } if not args.out: print('\nthe predicted result for the first element is ' f'pred_score = {pred_score[0]:.2f}, ' f'pred_label = {pred_label[0]} ' f'and pred_class = {pred_class[0]}. ' 'Specify --out to save all results to files.') if args.out: print(f'\nwriting results to {args.out}') mmcv.dump(results, args.out)
def main(): args = parse_args() # load test results outputs = mmcv.load(args.result) assert ('pred_score' in outputs and 'pred_class' in outputs and 'pred_label' in outputs), \ 'No "pred_label", "pred_score" or "pred_class" in result file, ' \ 'please set "--out-items" in test.py' cfg = mmcv.Config.fromfile(args.config) if args.cfg_options is not None: cfg.merge_from_dict(args.cfg_options) model = build_classifier(cfg.model) # build the dataloader dataset = build_dataset(cfg.data.test) filenames = list() for info in dataset.data_infos: if info['img_prefix'] is not None: filename = osp.join(info['img_prefix'], info['img_info']['filename']) else: filename = info['img_info']['filename'] filenames.append(filename) gt_labels = list(dataset.get_gt_labels()) gt_classes = [dataset.CLASSES[x] for x in gt_labels] outputs['filename'] = filenames outputs['gt_label'] = gt_labels outputs['gt_class'] = gt_classes outputs_list = list() for i in range(len(gt_labels)): output = dict() for k in outputs.keys(): output[k] = outputs[k][i] outputs_list.append(output) # sort result outputs_list = sorted(outputs_list, key=lambda x: x['pred_score']) success = list() fail = list() for output in outputs_list: if output['pred_label'] == output['gt_label']: success.append(output) else: fail.append(output) success = success[:args.topk] fail = fail[:args.topk] save_imgs(args.out_dir, 'success', success, model) save_imgs(args.out_dir, 'fail', fail, model)
def test_repeat_dataset(self): # Test build dataset = build_dataset( dict(type='RepeatDataset', dataset=self.dataset_cfg, times=3)) assert isinstance(dataset, RepeatDataset) assert dataset.dataset.test_mode == self.dataset_cfg['test_mode'] # Test default_args dataset = build_dataset( dict(type='RepeatDataset', dataset=self.dataset_cfg, times=3), {'test_mode': True}) assert dataset.dataset.test_mode == self.dataset_cfg['test_mode'] cp_cfg = deepcopy(self.dataset_cfg) cp_cfg.pop('test_mode') dataset = build_dataset( dict(type='RepeatDataset', dataset=cp_cfg, times=3), {'test_mode': True}) assert dataset.dataset.test_mode
def __init__(self, dataset_cfg, log_file_path, phase): super(DatasetValidator, self).__init__() # keep only LoadImageFromFile pipeline assert dataset_cfg.data[phase].pipeline[0][ 'type'] == 'LoadImageFromFile', 'This tool is only for dataset ' \ 'that needs to load image from files.' self.pipeline = PIPELINES.build(dataset_cfg.data[phase].pipeline[0]) dataset_cfg.data[phase].pipeline = [] dataset = build_dataset(dataset_cfg.data[phase]) self.dataset = dataset self.log_file_path = log_file_path
def read_random_data(self): train_dataset = build_dataset(self.cfg.data.train) print(F"train sample number: {len(train_dataset)}") train_dataloader = build_dataloader( dataset=train_dataset, samples_per_gpu=self.cfg.data.samples_per_gpu, workers_per_gpu=self.cfg.data.workers_per_gpu, num_gpus=1, dist=False, shuffle=False) data = next(iter(train_dataloader)) return data
def test_create_dataloader(self): train_dataset = build_dataset(self.cfg.data.train) print(F"train sample number: {len(train_dataset)}") train_dataloader = build_dataloader( dataset=train_dataset, samples_per_gpu=self.cfg.data.samples_per_gpu, workers_per_gpu=self.cfg.data.workers_per_gpu, num_gpus=2, dist=False, shuffle=False) for index, data in enumerate(train_dataloader): for k, v in data.items(): print(k, type(v.data[0])) print(data["img"].data.shape) print(data["gt_labels"].data) print(data["gt_angles"].data) break
def train_model(model, dataset, cfg, distributed=False, validate=False, timestamp=None, device=None, meta=None): logger = get_root_logger() # prepare data loaders dataset = dataset if isinstance(dataset, (list, tuple)) else [dataset] sampler_cfg = cfg.data.get('sampler', None) data_loaders = [ build_dataloader( ds, cfg.data.samples_per_gpu, cfg.data.workers_per_gpu, # cfg.gpus will be ignored if distributed num_gpus=len(cfg.gpu_ids), dist=distributed, round_up=True, seed=cfg.seed, sampler_cfg=sampler_cfg) for ds in dataset ] # put model on gpus if distributed: find_unused_parameters = cfg.get('find_unused_parameters', False) # Sets the `find_unused_parameters` parameter in # torch.nn.parallel.DistributedDataParallel model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False, find_unused_parameters=find_unused_parameters) else: if device == 'cpu': warnings.warn( 'The argument `device` is deprecated. To use cpu to train, ' 'please refers to https://mmclassification.readthedocs.io/en' '/latest/getting_started.html#train-a-model') model = model.cpu() else: model = MMDataParallel(model, device_ids=cfg.gpu_ids) if not model.device_ids: from mmcv import __version__, digit_version assert digit_version(__version__) >= (1, 4, 4), \ 'To train with CPU, please confirm your mmcv version ' \ 'is not lower than v1.4.4' # build runner optimizer = build_optimizer(model, cfg.optimizer) if cfg.get('runner') is None: cfg.runner = { 'type': 'EpochBasedRunner', 'max_epochs': cfg.total_epochs } warnings.warn( 'config is now expected to have a `runner` section, ' 'please set `runner` in your config.', UserWarning) runner = build_runner(cfg.runner, default_args=dict(model=model, batch_processor=None, optimizer=optimizer, work_dir=cfg.work_dir, logger=logger, meta=meta)) # an ugly walkaround to make the .log and .log.json filenames the same runner.timestamp = timestamp # fp16 setting fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: optimizer_config = Fp16OptimizerHook(**cfg.optimizer_config, **fp16_cfg, distributed=distributed) elif distributed and 'type' not in cfg.optimizer_config: optimizer_config = DistOptimizerHook(**cfg.optimizer_config) else: optimizer_config = cfg.optimizer_config # register hooks runner.register_training_hooks(cfg.lr_config, optimizer_config, cfg.checkpoint_config, cfg.log_config, cfg.get('momentum_config', None), custom_hooks_config=cfg.get( 'custom_hooks', None)) if distributed and cfg.runner['type'] == 'EpochBasedRunner': runner.register_hook(DistSamplerSeedHook()) # register eval hooks if validate: val_dataset = build_dataset(cfg.data.val, dict(test_mode=True)) val_dataloader = build_dataloader( val_dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=True) eval_cfg = cfg.get('evaluation', {}) eval_cfg['by_epoch'] = cfg.runner['type'] != 'IterBasedRunner' eval_hook = DistEvalHook if distributed else EvalHook # `EvalHook` needs to be executed after `IterTimerHook`. # Otherwise, it will cause a bug if use `IterBasedRunner`. # Refers to https://github.com/open-mmlab/mmcv/issues/1261 runner.register_hook(eval_hook(val_dataloader, **eval_cfg), priority='LOW') if cfg.resume_from: runner.resume(cfg.resume_from) elif cfg.load_from: runner.load_checkpoint(cfg.load_from) runner.run(data_loaders, cfg.workflow)
def main(): args = parse_args() cfg = Config.fromfile(args.config) if args.cfg_options is not None: cfg.merge_from_dict(args.cfg_options) # set multi-process settings setup_multi_processes(cfg) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True # work_dir is determined in this priority: CLI > segment in file > filename if args.work_dir is not None: # update configs according to CLI args if args.work_dir is not None cfg.work_dir = args.work_dir elif cfg.get('work_dir', None) is None: # use config filename as default work_dir if cfg.work_dir is None cfg.work_dir = osp.join('./work_dirs', osp.splitext(osp.basename(args.config))[0]) if args.resume_from is not None: cfg.resume_from = args.resume_from if args.gpus is not None: cfg.gpu_ids = range(1) warnings.warn('`--gpus` is deprecated because we only support ' 'single GPU mode in non-distributed training. ' 'Use `gpus=1` now.') if args.gpu_ids is not None: cfg.gpu_ids = args.gpu_ids[0:1] warnings.warn('`--gpu-ids` is deprecated, please use `--gpu-id`. ' 'Because we only support single GPU mode in ' 'non-distributed training. Use the first GPU ' 'in `gpu_ids` now.') if args.gpus is None and args.gpu_ids is None: cfg.gpu_ids = [args.gpu_id] # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) _, world_size = get_dist_info() cfg.gpu_ids = range(world_size) # create work_dir mmcv.mkdir_or_exist(osp.abspath(cfg.work_dir)) # dump config cfg.dump(osp.join(cfg.work_dir, osp.basename(args.config))) # init the logger before other steps timestamp = time.strftime('%Y%m%d_%H%M%S', time.localtime()) log_file = osp.join(cfg.work_dir, f'{timestamp}.log') logger = get_root_logger(log_file=log_file, log_level=cfg.log_level) # init the meta dict to record some important information such as # environment info and seed, which will be logged meta = dict() # log env info env_info_dict = collect_env() env_info = '\n'.join([(f'{k}: {v}') for k, v in env_info_dict.items()]) dash_line = '-' * 60 + '\n' logger.info('Environment info:\n' + dash_line + env_info + '\n' + dash_line) meta['env_info'] = env_info # log some basic info logger.info(f'Distributed training: {distributed}') logger.info(f'Config:\n{cfg.pretty_text}') # set random seeds seed = init_random_seed(args.seed) logger.info(f'Set random seed to {seed}, ' f'deterministic: {args.deterministic}') set_random_seed(seed, deterministic=args.deterministic) cfg.seed = seed meta['seed'] = seed model = build_classifier(cfg.model) model.init_weights() datasets = [build_dataset(cfg.data.train)] if len(cfg.workflow) == 2: val_dataset = copy.deepcopy(cfg.data.val) val_dataset.pipeline = cfg.data.train.pipeline datasets.append(build_dataset(val_dataset)) # save mmcls version, config file content and class names in # runner as meta data meta.update( dict(mmcls_version=__version__, config=cfg.pretty_text, CLASSES=datasets[0].CLASSES)) # add an attribute for visualization convenience train_model(model, datasets, cfg, distributed=distributed, validate=(not args.no_validate), timestamp=timestamp, device='cpu' if args.device == 'cpu' else 'cuda', meta=meta)
def main(): args = parse_args() cfg = mmcv.Config.fromfile(args.config) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True cfg.model.pretrained = None cfg.data.test.test_mode = True # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) # build the dataloader dataset = build_dataset(cfg.data.test) data_loader = build_dataloader(dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=False) # build the model and load checkpoint model = build_classifier(cfg.model) fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: wrap_fp16_model(model) _ = load_checkpoint(model, args.checkpoint, map_location='cpu') if not distributed: model = MMDataParallel(model, device_ids=[0]) outputs = single_gpu_test(model, data_loader) else: model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False) outputs = multi_gpu_test(model, data_loader, args.tmpdir, args.gpu_collect) rank, _ = get_dist_info() if rank == 0: nums = [] results = {} for output in outputs: nums.append(output['num_samples'].item()) for topk, v in output['accuracy'].items(): if topk not in results: results[topk] = [] results[topk].append(v.item()) assert sum(nums) == len(dataset) for topk, accs in results.items(): avg_acc = np.average(accs, weights=nums) print(f'\n{topk} accuracy: {avg_acc:.2f}') if args.out and rank == 0: print(f'\nwriting results to {args.out}') mmcv.dump(outputs, args.out)
def train_model(model, dataset, cfg, distributed=False, validate=False, timestamp=None, device='cuda', meta=None): logger = get_root_logger(cfg.log_level) # prepare data loaders dataset = dataset if isinstance(dataset, (list, tuple)) else [dataset] data_loaders = [ build_dataloader( ds, cfg.data.samples_per_gpu, cfg.data.workers_per_gpu, # cfg.gpus will be ignored if distributed num_gpus=len(cfg.gpu_ids), dist=distributed, round_up=True, seed=cfg.seed) for ds in dataset ] # put model on gpus if distributed: find_unused_parameters = cfg.get('find_unused_parameters', False) # Sets the `find_unused_parameters` parameter in # torch.nn.parallel.DistributedDataParallel model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False, find_unused_parameters=find_unused_parameters) else: if device == 'cuda': model = MMDataParallel(model.cuda(cfg.gpu_ids[0]), device_ids=cfg.gpu_ids) elif device == 'cpu': model = model.cpu() else: raise ValueError(F'unsupported device name {device}.') # build runner optimizer = build_optimizer(model, cfg.optimizer) if cfg.get('runner') is None: cfg.runner = { 'type': 'EpochBasedRunner', 'max_epochs': cfg.total_epochs } warnings.warn( 'config is now expected to have a `runner` section, ' 'please set `runner` in your config.', UserWarning) runner = build_runner(cfg.runner, default_args=dict(model=model, batch_processor=None, optimizer=optimizer, work_dir=cfg.work_dir, logger=logger, meta=meta)) # an ugly walkaround to make the .log and .log.json filenames the same runner.timestamp = timestamp # fp16 setting fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: optimizer_config = Fp16OptimizerHook(**cfg.optimizer_config, **fp16_cfg, distributed=distributed) elif distributed and 'type' not in cfg.optimizer_config: optimizer_config = DistOptimizerHook(**cfg.optimizer_config) else: optimizer_config = cfg.optimizer_config # register hooks runner.register_training_hooks(cfg.lr_config, optimizer_config, cfg.checkpoint_config, cfg.log_config, cfg.get('momentum_config', None), custom_hooks_config=cfg.get( 'custom_hooks', None)) if distributed: runner.register_hook(DistSamplerSeedHook()) # register eval hooks if validate: val_dataset = build_dataset(cfg.data.val, dict(test_mode=True)) val_dataloader = build_dataloader( val_dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=True) eval_cfg = cfg.get('evaluation', {}) eval_cfg['by_epoch'] = cfg.runner['type'] != 'IterBasedRunner' eval_hook = DistEvalHook if distributed else EvalHook runner.register_hook(eval_hook(val_dataloader, **eval_cfg)) if cfg.resume_from: runner.resume(cfg.resume_from) elif cfg.load_from: runner.load_checkpoint(cfg.load_from) runner.run(data_loaders, cfg.workflow)
def train_model(model, dataset, cfg, distributed=False, validate=False, timestamp=None, meta=None): logger = get_root_logger(cfg.log_level) # prepare data loaders dataset = dataset if isinstance(dataset, (list, tuple)) else [dataset] data_loaders = [ build_dataloader( ds, cfg.data.samples_per_gpu, cfg.data.workers_per_gpu, # cfg.gpus will be ignored if distributed num_gpus=len(cfg.gpu_ids), dist=distributed, round_up=True, seed=cfg.seed) for ds in dataset ] # put model on gpus if distributed: find_unused_parameters = cfg.get('find_unused_parameters', False) # Sets the `find_unused_parameters` parameter in # torch.nn.parallel.DistributedDataParallel model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False, find_unused_parameters=find_unused_parameters) else: model = MMDataParallel( model.cuda(cfg.gpu_ids[0]), device_ids=cfg.gpu_ids) # build runner optimizer = build_optimizer(model, cfg.optimizer) runner = Runner( model, optimizer=optimizer, work_dir=cfg.work_dir, logger=logger, meta=meta, ema_cfg=cfg.get('ema_cfg', None)) # an ugly walkaround to make the .log and .log.json filenames the same runner.timestamp = timestamp # fp16 setting fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: optimizer_config = Fp16OptimizerHook( **cfg.optimizer_config, **fp16_cfg, distributed=distributed) elif distributed and 'type' not in cfg.optimizer_config: optimizer_config = DistOptimizerHook(**cfg.optimizer_config) else: optimizer_config = cfg.optimizer_config # register hooks runner.register_training_hooks(cfg.lr_config, optimizer_config, cfg.checkpoint_config, cfg.log_config, cfg.get('momentum_config', None)) if distributed: runner.register_hook(DistSamplerSeedHook()) # register eval hooks if validate: val_dataset = build_dataset(cfg.data.val, dict(test_mode=True)) val_dataloader = build_dataloader( val_dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=False) eval_cfg = cfg.get('evaluation', {}) eval_hook = DistEvalHook if distributed else EvalHook runner.register_hook(eval_hook(val_dataloader, **eval_cfg)) if cfg.resume_from: runner.resume(cfg.resume_from) elif cfg.load_from: runner.load_checkpoint(cfg.load_from) runner.run(data_loaders, cfg.workflow, cfg.total_epochs)
def main(): args = parse_args() cfg = mmcv.Config.fromfile(args.config) if args.options is not None: cfg.merge_from_dict(args.options) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True cfg.model.pretrained = None cfg.data.test.test_mode = True # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) # build the dataloader dataset = build_dataset(cfg.data.test) data_loader = build_dataloader(dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=False) # build the model and load checkpoint model = build_classifier(cfg.model) fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: wrap_fp16_model(model) checkpoint = load_checkpoint(model, args.checkpoint, map_location='cpu') if not distributed: model = MMDataParallel(model, device_ids=[0]) outputs = single_gpu_test(model, data_loader) else: model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False) outputs = multi_gpu_test(model, data_loader, args.tmpdir, args.gpu_collect) rank, _ = get_dist_info() if rank == 0: if args.metrics: results = dataset.evaluate(outputs, args.metrics, args.metric_options) for k, v in results.items(): print(f'\n{k} : {v:.2f}') else: warnings.warn('Evaluation metrics are not specified.') scores = np.vstack(outputs) pred_score = np.max(scores, axis=1) pred_label = np.argmax(scores, axis=1) if 'CLASSES' in checkpoint['meta']: CLASSES = checkpoint['meta']['CLASSES'] else: from mmcls.datasets import ImageNet warnings.simplefilter('once') warnings.warn('Class names are not saved in the checkpoint\'s ' 'meta data, use imagenet by default.') CLASSES = ImageNet.CLASSES pred_class = [CLASSES[lb] for lb in pred_label] results = { 'pred_score': pred_score, 'pred_label': pred_label, 'pred_class': pred_class } if not args.out: print('\nthe predicted result for the first element is ' f'pred_score = {pred_score[0]:.2f}, ' f'pred_label = {pred_label[0]} ' f'and pred_class = {pred_class[0]}. ' 'Specify --out to save all results to files.') if args.out and rank == 0: print(f'\nwriting results to {args.out}') mmcv.dump(results, args.out)
def main(): args = parse_args() cfg = mmcv.Config.fromfile(args.config) if args.cfg_options is not None: cfg.merge_from_dict(args.cfg_options) # set multi-process settings setup_multi_processes(cfg) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True cfg.model.pretrained = None if args.gpu_ids is not None: cfg.gpu_ids = args.gpu_ids[0:1] warnings.warn('`--gpu-ids` is deprecated, please use `--gpu-id`. ' 'Because we only support single GPU mode in ' 'non-distributed testing. Use the first GPU ' 'in `gpu_ids` now.') else: cfg.gpu_ids = [args.gpu_id] # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) # build the dataloader dataset = build_dataset(cfg.data.test, default_args=dict(test_mode=True)) # the extra round_up data will be removed during gpu/cpu collect data_loader = build_dataloader(dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=True) # build the model and load checkpoint model = build_classifier(cfg.model) fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: wrap_fp16_model(model) checkpoint = load_checkpoint(model, args.checkpoint, map_location='cpu') if 'CLASSES' in checkpoint.get('meta', {}): CLASSES = checkpoint['meta']['CLASSES'] else: from mmcls.datasets import ImageNet warnings.simplefilter('once') warnings.warn('Class names are not saved in the checkpoint\'s ' 'meta data, use imagenet by default.') CLASSES = ImageNet.CLASSES if not distributed: if args.device == 'cpu': model = model.cpu() else: model = MMDataParallel(model, device_ids=cfg.gpu_ids) if not model.device_ids: assert mmcv.digit_version(mmcv.__version__) >= (1, 4, 4), \ 'To test with CPU, please confirm your mmcv version ' \ 'is not lower than v1.4.4' model.CLASSES = CLASSES show_kwargs = {} if args.show_options is None else args.show_options outputs = single_gpu_test(model, data_loader, args.show, args.show_dir, **show_kwargs) else: model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False) outputs = multi_gpu_test(model, data_loader, args.tmpdir, args.gpu_collect) rank, _ = get_dist_info() if rank == 0: results = {} logger = get_root_logger() if args.metrics: eval_results = dataset.evaluate(results=outputs, metric=args.metrics, metric_options=args.metric_options, logger=logger) results.update(eval_results) for k, v in eval_results.items(): if isinstance(v, np.ndarray): v = [round(out, 2) for out in v.tolist()] elif isinstance(v, Number): v = round(v, 2) else: raise ValueError(f'Unsupport metric type: {type(v)}') print(f'\n{k} : {v}') if args.out: if 'none' not in args.out_items: scores = np.vstack(outputs) pred_score = np.max(scores, axis=1) pred_label = np.argmax(scores, axis=1) pred_class = [CLASSES[lb] for lb in pred_label] res_items = { 'class_scores': scores, 'pred_score': pred_score, 'pred_label': pred_label, 'pred_class': pred_class } if 'all' in args.out_items: results.update(res_items) else: for key in args.out_items: results[key] = res_items[key] print(f'\ndumping results to {args.out}') mmcv.dump(results, args.out)
dict(type='ToTensor', keys=['img']), dict(type='SpecCutout', keys=['img'], f_mask=8, t_mask=10), dict(type='Collect', keys=['img', 'gt_label']) ] test_pipeline = [ # dict(type='ToTensor', keys=['gt_label']), dict(type='ToTensor', keys=['img']), dict(type='Collect', keys=['img']) ] data = dict(samples_per_gpu=128, workers_per_gpu=2, train=dict(type=dataset_type, data_prefix='/data1/mayufeng/data_vox/train', pipeline=train_pipeline, map="/data1/mayufeng/data_vox/train/uid2classes.json"), val=dict(type=dataset_type, data_prefix='/data1/mayufeng/data_vox/val', pipeline=test_pipeline, map="/data1/mayufeng/data_vox/train/uid2classes.json"), test=dict(type=dataset_type, data_prefix='/data1/mayufeng/data_vox/val', pipeline=test_pipeline, map="/data1/mayufeng/data_vox/train/uid2classes.json")) if __name__ == "__main__": from mmcls.datasets import build_dataset dataset = build_dataset(data["train"]) dataset.test_mode = True print(dataset[1000])
def train_single_fold(args, cfg, fold, distributed, seed): # create the work_dir for the fold work_dir = osp.join(cfg.work_dir, f'fold{fold}') cfg.work_dir = work_dir # create work_dir mmcv.mkdir_or_exist(osp.abspath(cfg.work_dir)) # wrap the dataset cfg train_dataset = dict( type='KFoldDataset', fold=fold, dataset=cfg.data.train, num_splits=args.num_splits, seed=seed, ) val_dataset = dict( type='KFoldDataset', fold=fold, # Use the same dataset with training. dataset=copy.deepcopy(cfg.data.train), num_splits=args.num_splits, seed=seed, test_mode=True, ) val_dataset['dataset']['pipeline'] = cfg.data.val.pipeline cfg.data.train = train_dataset cfg.data.val = val_dataset cfg.data.test = val_dataset # dump config stem, suffix = osp.basename(args.config).rsplit('.', 1) cfg.dump(osp.join(cfg.work_dir, f'{stem}_fold{fold}.{suffix}')) # init the logger before other steps timestamp = time.strftime('%Y%m%d_%H%M%S', time.localtime()) log_file = osp.join(cfg.work_dir, f'{timestamp}.log') logger = get_root_logger(log_file=log_file, log_level=cfg.log_level) # init the meta dict to record some important information such as # environment info and seed, which will be logged meta = dict() # log env info env_info_dict = collect_env() env_info = '\n'.join([(f'{k}: {v}') for k, v in env_info_dict.items()]) dash_line = '-' * 60 + '\n' logger.info('Environment info:\n' + dash_line + env_info + '\n' + dash_line) meta['env_info'] = env_info # log some basic info logger.info(f'Distributed training: {distributed}') logger.info(f'Config:\n{cfg.pretty_text}') logger.info( f'-------- Cross-validation: [{fold+1}/{args.num_splits}] -------- ') # set random seeds # Use different seed in different folds logger.info(f'Set random seed to {seed + fold}, ' f'deterministic: {args.deterministic}') set_random_seed(seed + fold, deterministic=args.deterministic) cfg.seed = seed + fold meta['seed'] = seed + fold model = build_classifier(cfg.model) model.init_weights() datasets = [build_dataset(cfg.data.train)] if len(cfg.workflow) == 2: val_dataset = copy.deepcopy(cfg.data.val) val_dataset.pipeline = cfg.data.train.pipeline datasets.append(build_dataset(val_dataset)) meta.update( dict(mmcls_version=__version__, config=cfg.pretty_text, CLASSES=datasets[0].CLASSES, kfold=dict(fold=fold, num_splits=args.num_splits))) # add an attribute for visualization convenience train_model(model, datasets, cfg, distributed=distributed, validate=(not args.no_validate), timestamp=timestamp, device='cpu' if args.device == 'cpu' else 'cuda', meta=meta)
def main(): args = parse_args() cfg = mmcv.Config.fromfile(args.config) if args.options is not None: cfg.merge_from_dict(args.options) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True cfg.model.pretrained = None cfg.data.test.test_mode = True assert args.metrics or args.out, \ 'Please specify at least one of output path and evaluation metrics.' # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) # build the dataloader dataset = build_dataset(cfg.data.test) # the extra round_up data will be removed during gpu/cpu collect data_loader = build_dataloader(dataset, samples_per_gpu=cfg.data.samples_per_gpu, workers_per_gpu=cfg.data.workers_per_gpu, dist=distributed, shuffle=False, round_up=True) # build the model and load checkpoint model = build_classifier(cfg.model) fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: wrap_fp16_model(model) checkpoint = load_checkpoint(model, args.checkpoint, map_location='cpu') if 'CLASSES' in checkpoint.get('meta', {}): CLASSES = checkpoint['meta']['CLASSES'] else: from mmcls.datasets import ImageNet warnings.simplefilter('once') warnings.warn('Class names are not saved in the checkpoint\'s ' 'meta data, use imagenet by default.') CLASSES = ImageNet.CLASSES if not distributed: if args.device == 'cpu': model = model.cpu() else: model = MMDataParallel(model, device_ids=[0]) model.CLASSES = CLASSES show_kwargs = {} if args.show_options is None else args.show_options outputs = single_gpu_test(model, data_loader, args.show, args.show_dir, **show_kwargs) else: model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False) outputs = multi_gpu_test(model, data_loader, args.tmpdir, args.gpu_collect) rank, _ = get_dist_info() if rank == 0: results = {} if args.metrics: eval_results = dataset.evaluate(outputs, args.metrics, args.metric_options) results.update(eval_results) for k, v in eval_results.items(): print(f'\n{k} : {v:.2f}') if args.out: scores = np.vstack(outputs) pred_score = np.max(scores, axis=1) pred_label = np.argmax(scores, axis=1) pred_class = [CLASSES[lb] for lb in pred_label] results.update({ 'class_scores': scores, 'pred_score': pred_score, 'pred_label': pred_label, 'pred_class': pred_class }) print(f'\ndumping results to {args.out}') mmcv.dump(results, args.out)
def main(): args = parse_args() cfg = Config.fromfile(args.config) if args.options is not None: cfg.merge_from_dict(args.options) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True if args.net_params: tag, input_channels, block1, block2, block3, block4, last_channel = args.net_params.split('-') input_channels = [int(item) for item in input_channels.split('_')] block1 = [int(item) for item in block1.split('_')] block2 = [int(item) for item in block2.split('_')] block3 = [int(item) for item in block3.split('_')] block4 = [int(item) for item in block4.split('_')] last_channel = int(last_channel) inverted_residual_setting = [] for item in [block1, block2, block3, block4]: for _ in range(item[0]): inverted_residual_setting.append([item[1], item[2:-int(len(item)/2-1)], item[-int(len(item)/2-1):]]) cfg.model.backbone.input_channel = input_channels cfg.model.backbone.inverted_residual_setting = inverted_residual_setting cfg.model.backbone.last_channel = last_channel cfg.model.head.in_channels = last_channel # work_dir is determined in this priority: CLI > segment in file > filename if args.work_dir is not None: # update configs according to CLI args if args.work_dir is not None cfg.work_dir = args.work_dir elif cfg.get('work_dir', None) is None: # use config filename as default work_dir if cfg.work_dir is None cfg.work_dir = osp.join('./work_dirs', osp.splitext(osp.basename(args.config))[0]) if args.resume_from is not None: cfg.resume_from = args.resume_from if args.gpu_ids is not None: cfg.gpu_ids = args.gpu_ids else: cfg.gpu_ids = range(1) if args.gpus is None else range(args.gpus) if args.autoscale_lr: # apply the linear scaling rule (https://arxiv.org/abs/1706.02677) cfg.optimizer['lr'] = cfg.optimizer['lr'] * len(cfg.gpu_ids) / 8 # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) # create work_dir mmcv.mkdir_or_exist(osp.abspath(cfg.work_dir)) # init the logger before other steps timestamp = time.strftime('%Y%m%d_%H%M%S', time.localtime()) if args.net_params: log_file = osp.join(cfg.work_dir, f'{args.net_params}.log') else: log_file = osp.join(cfg.work_dir, f'{timestamp}.log') logger = get_root_logger(log_file=log_file, log_level=cfg.log_level) # init the meta dict to record some important information such as # environment info and seed, which will be logged meta = dict() # log env info env_info_dict = collect_env() env_info = '\n'.join([(f'{k}: {v}') for k, v in env_info_dict.items()]) dash_line = '-' * 60 + '\n' logger.info('Environment info:\n' + dash_line + env_info + '\n' + dash_line) meta['env_info'] = env_info # log some basic info logger.info(f'Distributed training: {distributed}') logger.info(f'Config:\n{cfg.pretty_text}') # set random seeds if args.seed is not None: logger.info(f'Set random seed to {args.seed}, ' f'deterministic: {args.deterministic}') set_random_seed(args.seed, deterministic=args.deterministic) cfg.seed = args.seed meta['seed'] = args.seed model = build_classifier(cfg.model) datasets = [build_dataset(cfg.data.train)] if len(cfg.workflow) == 2: val_dataset = copy.deepcopy(cfg.data.val) val_dataset.pipeline = cfg.data.train.pipeline datasets.append(build_dataset(val_dataset)) if cfg.checkpoint_config is not None: # save mmcls version, config file content and class names in # checkpoints as meta data cfg.checkpoint_config.meta = dict( mmcls_version=__version__, config=cfg.pretty_text, CLASSES=datasets[0].CLASSES) # add an attribute for visualization convenience train_model( model, datasets, cfg, distributed=distributed, validate=(not args.no_validate), timestamp=timestamp, meta=meta)
def main(): print("--------> 1") args = parse_args() print("--------> 2") cfg = Config.fromfile(args.config) print("--------> 3") if args.options is not None: cfg.merge_from_dict(args.options) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True print("--------> 4") # work_dir is determined in this priority: CLI > segment in file > filename if args.work_dir is not None: # update configs according to CLI args if args.work_dir is not None cfg.work_dir = args.work_dir elif cfg.get('work_dir', None) is None: # use config filename as default work_dir if cfg.work_dir is None cfg.work_dir = osp.join('./work_dirs', osp.splitext(osp.basename(args.config))[0]) if args.resume_from is not None: cfg.resume_from = args.resume_from if args.gpu_ids is not None: cfg.gpu_ids = args.gpu_ids else: cfg.gpu_ids = range(1) if args.gpus is None else range(args.gpus) print("--------> 5") # init distributed env first, since logger depends on the dist info. if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) _, world_size = get_dist_info() cfg.gpu_ids = range(world_size) print("--------> 6") # create work_dir mmcv.mkdir_or_exist(osp.abspath(cfg.work_dir)) # init the logger before other steps timestamp = time.strftime('%Y%m%d_%H%M%S', time.localtime()) log_file = osp.join(cfg.work_dir, f'{timestamp}.log') logger = get_root_logger(log_file=log_file, log_level=cfg.log_level) print("--------> 7") # init the meta dict to record some important information such as # environment info and seed, which will be logged meta = dict() # log env info env_info_dict = collect_env() env_info = '\n'.join([(f'{k}: {v}') for k, v in env_info_dict.items()]) dash_line = '-' * 60 + '\n' logger.info('Environment info:\n' + dash_line + env_info + '\n' + dash_line) meta['env_info'] = env_info # log some basic info cfg_pretty_text = cfg.pretty_text logger.info(f'Distributed training: {distributed}') logger.info(f'Config:\n{cfg_pretty_text}') # set random seeds if args.seed is not None: logger.info(f'Set random seed to {args.seed}, ' f'deterministic: {args.deterministic}') set_random_seed(args.seed, deterministic=args.deterministic) cfg.seed = args.seed meta['seed'] = args.seed model = build_classifier(cfg.model) datasets = [build_dataset(cfg.data.train)] if len(cfg.workflow) == 2: val_dataset = copy.deepcopy(cfg.data.val) val_dataset.pipeline = cfg.data.train.pipeline datasets.append(build_dataset(val_dataset)) if cfg.checkpoint_config is not None: # save mmcls version, config file content and class names in # checkpoints as meta data cfg.checkpoint_config.meta = dict(mmcls_version=__version__, config=cfg_pretty_text, CLASSES=datasets[0].CLASSES) model.CLASSES = datasets[0].CLASSES # add an attribute for visualization convenience train_model(model, datasets, cfg, distributed=distributed, validate=(not args.no_validate), timestamp=timestamp, device='cpu' if args.device == 'cpu' else 'cuda', meta=meta)
def train_model(model, dataset, cfg, distributed=False, validate=False, timestamp=None, device=None, meta=None): """Train a model. This method will build dataloaders, wrap the model and build a runner according to the provided config. Args: model (:obj:`torch.nn.Module`): The model to be run. dataset (:obj:`mmcls.datasets.BaseDataset` | List[BaseDataset]): The dataset used to train the model. It can be a single dataset, or a list of dataset with the same length as workflow. cfg (:obj:`mmcv.utils.Config`): The configs of the experiment. distributed (bool): Whether to train the model in a distributed environment. Defaults to False. validate (bool): Whether to do validation with :obj:`mmcv.runner.EvalHook`. Defaults to False. timestamp (str, optional): The timestamp string to auto generate the name of log files. Defaults to None. device (str, optional): TODO meta (dict, optional): A dict records some import information such as environment info and seed, which will be logged in logger hook. Defaults to None. """ logger = get_root_logger() # prepare data loaders dataset = dataset if isinstance(dataset, (list, tuple)) else [dataset] # The default loader config loader_cfg = dict( # cfg.gpus will be ignored if distributed num_gpus=cfg.ipu_replicas if device == 'ipu' else len(cfg.gpu_ids), dist=distributed, round_up=True, seed=cfg.get('seed'), sampler_cfg=cfg.get('sampler', None), ) # The overall dataloader settings loader_cfg.update({ k: v for k, v in cfg.data.items() if k not in [ 'train', 'val', 'test', 'train_dataloader', 'val_dataloader', 'test_dataloader' ] }) # The specific dataloader settings train_loader_cfg = {**loader_cfg, **cfg.data.get('train_dataloader', {})} data_loaders = [build_dataloader(ds, **train_loader_cfg) for ds in dataset] # put model on gpus if distributed: find_unused_parameters = cfg.get('find_unused_parameters', False) # Sets the `find_unused_parameters` parameter in # torch.nn.parallel.DistributedDataParallel model = MMDistributedDataParallel( model.cuda(), device_ids=[torch.cuda.current_device()], broadcast_buffers=False, find_unused_parameters=find_unused_parameters) else: if device == 'cpu': warnings.warn( 'The argument `device` is deprecated. To use cpu to train, ' 'please refers to https://mmclassification.readthedocs.io/en' '/latest/getting_started.html#train-a-model') model = model.cpu() elif device == 'ipu': model = model.cpu() else: model = MMDataParallel(model, device_ids=cfg.gpu_ids) if not model.device_ids: from mmcv import __version__, digit_version assert digit_version(__version__) >= (1, 4, 4), \ 'To train with CPU, please confirm your mmcv version ' \ 'is not lower than v1.4.4' # build runner optimizer = build_optimizer(model, cfg.optimizer) if cfg.get('runner') is None: cfg.runner = { 'type': 'EpochBasedRunner', 'max_epochs': cfg.total_epochs } warnings.warn( 'config is now expected to have a `runner` section, ' 'please set `runner` in your config.', UserWarning) if device == 'ipu': if not cfg.runner['type'].startswith('IPU'): cfg.runner['type'] = 'IPU' + cfg.runner['type'] if 'options_cfg' not in cfg.runner: cfg.runner['options_cfg'] = {} cfg.runner['options_cfg']['replicationFactor'] = cfg.ipu_replicas cfg.runner['fp16_cfg'] = cfg.get('fp16', None) runner = build_runner(cfg.runner, default_args=dict(model=model, batch_processor=None, optimizer=optimizer, work_dir=cfg.work_dir, logger=logger, meta=meta)) # an ugly walkaround to make the .log and .log.json filenames the same runner.timestamp = timestamp # fp16 setting fp16_cfg = cfg.get('fp16', None) if fp16_cfg is not None: if device == 'ipu': from mmcv.device.ipu import IPUFp16OptimizerHook optimizer_config = IPUFp16OptimizerHook( **cfg.optimizer_config, loss_scale=fp16_cfg['loss_scale'], distributed=distributed) else: optimizer_config = Fp16OptimizerHook( **cfg.optimizer_config, loss_scale=fp16_cfg['loss_scale'], distributed=distributed) elif distributed and 'type' not in cfg.optimizer_config: optimizer_config = DistOptimizerHook(**cfg.optimizer_config) else: optimizer_config = cfg.optimizer_config # register hooks runner.register_training_hooks(cfg.lr_config, optimizer_config, cfg.checkpoint_config, cfg.log_config, cfg.get('momentum_config', None), custom_hooks_config=cfg.get( 'custom_hooks', None)) if distributed and cfg.runner['type'] == 'EpochBasedRunner': runner.register_hook(DistSamplerSeedHook()) # register eval hooks if validate: val_dataset = build_dataset(cfg.data.val, dict(test_mode=True)) # The specific dataloader settings val_loader_cfg = { **loader_cfg, 'shuffle': False, # Not shuffle by default 'sampler_cfg': None, # Not use sampler by default **cfg.data.get('val_dataloader', {}), } val_dataloader = build_dataloader(val_dataset, **val_loader_cfg) eval_cfg = cfg.get('evaluation', {}) eval_cfg['by_epoch'] = cfg.runner['type'] != 'IterBasedRunner' eval_hook = DistEvalHook if distributed else EvalHook # `EvalHook` needs to be executed after `IterTimerHook`. # Otherwise, it will cause a bug if use `IterBasedRunner`. # Refers to https://github.com/open-mmlab/mmcv/issues/1261 runner.register_hook(eval_hook(val_dataloader, **eval_cfg), priority='LOW') if cfg.resume_from: runner.resume(cfg.resume_from) elif cfg.load_from: runner.load_checkpoint(cfg.load_from) runner.run(data_loaders, cfg.workflow)
def main(): args = parse_args() cfg = Config.fromfile(args.config) if args.options is not None: cfg.merge_from_dict(args.options) # set cudnn_benchmark if cfg.get('cudnn_benchmark', False): torch.backends.cudnn.benchmark = True if args.work_dir is not None: # update configs according to CLI args if args.work_dir is not None cfg.work_dir = args.work_dir elif cfg.get('work_dir', None) is None: # use config filename as default work_dir if cfg.work_dir is None cfg.work_dir = osp.join('./work_dirs', osp.splitext(osp.basename(args.config))[0]) if args.aml: data_store = os.environ['AZUREML_DATAREFERENCE_{}'.format( args.aml_data_store)] parse(cfg, data_store) if cfg.resume_from is not None: cfg.resume_from = os.path.join(data_store, args.aml_work_dir_prefix, cfg.resume_from) cfg.work_dir = os.path.join(data_store, args.aml_work_dir_prefix, cfg.work_dir) print('work_dir: ', cfg.work_dir) if 'data' in cfg.model.pretrained: cfg.model.pretrained = os.path.join(data_store, cfg.model.pretrained) # if not args.aml: # # work_dir is determined in this priority: CLI > segment in file > filename # if args.work_dir is not None: # # update configs according to CLI args if args.work_dir is not None # cfg.work_dir = args.work_dir # elif cfg.get('work_dir', None) is None: # # use config filename as default work_dir if cfg.work_dir is None # cfg.work_dir = osp.join('./work_dirs', # osp.splitext(osp.basename(args.config))[0]) if args.resume_from is not None: cfg.resume_from = args.resume_from if args.gpu_ids is not None: cfg.gpu_ids = args.gpu_ids else: cfg.gpu_ids = range(1) if args.gpus is None else range(args.gpus) if args.launcher == 'none': distributed = False else: distributed = True init_dist(args.launcher, **cfg.dist_params) # update gpu num if dist.is_initialized(): cfg.gpus = dist.get_world_size() else: cfg.gpus = args.gpus if args.autoscale_lr: # apply the linear scaling rule (https://arxiv.org/abs/1706.02677) cfg.optimizer['lr'] = cfg.optimizer[ 'lr'] * cfg.gpus / 8 * cfg.data.samples_per_gpu / 32 # create work_dir mmcv.mkdir_or_exist(osp.abspath(cfg.work_dir)) # init the logger before other steps timestamp = time.strftime('%Y%m%d_%H%M%S', time.localtime()) log_file = osp.join(cfg.work_dir, f'{timestamp}.log') logger = get_root_logger(log_file=log_file, log_level=cfg.log_level) # init the meta dict to record some important information such as # environment info and seed, which will be logged meta = dict() # log env info env_info_dict = collect_env() env_info = '\n'.join([(f'{k}: {v}') for k, v in env_info_dict.items()]) dash_line = '-' * 60 + '\n' logger.info('Environment info:\n' + dash_line + env_info + '\n' + dash_line) meta['env_info'] = env_info # log some basic info logger.info(f'Distributed training: {distributed}') logger.info(f'Config:\n{cfg.pretty_text}') # set random seeds if args.seed is not None: logger.info(f'Set random seed to {args.seed}, ' f'deterministic: {args.deterministic}') set_random_seed(args.seed, deterministic=args.deterministic) cfg.seed = args.seed meta['seed'] = args.seed model = build_classifier(cfg.model) datasets = [build_dataset(cfg.data.train)] if len(cfg.workflow) == 2: val_dataset = copy.deepcopy(cfg.data.val) val_dataset.pipeline = cfg.data.train.pipeline datasets.append(build_dataset(val_dataset)) if cfg.checkpoint_config is not None: # save mmcls version, config file content and class names in # checkpoints as meta data cfg.checkpoint_config.meta = dict(mmcls_version=__version__, config=cfg.pretty_text, CLASSES=datasets[0].CLASSES) # add an attribute for visualization convenience train_model(model, datasets, cfg, distributed=distributed, validate=(not args.no_validate), timestamp=timestamp, meta=meta)
def test_dataset_sample_number(self): train_dataset = build_dataset(self.cfg.data.train) print(F"train sample number: {len(train_dataset)}")