def on_init(self, **kwargs):
        mode = kwargs.get('mode', None)
        input_transform_dir = kwargs.get('input_image_transformation', None)
        self.transform = self.get_transforms(input_transform_dir, mode)
        logger.info(f'{mode}, transforms {self.transform}.')

        logger.info("Transformation init finished.")
 def run(self, **kwargs):
     input_image_dir = kwargs.get('input_image_directory', None)
     logger.info(f'Applying transform:')
     transformed_dir = input_image_dir.apply_to_images(
         transform=lambda image: self.unloader(
             self.transform(image).squeeze(0)).convert("RGB"))
     return (transformed_dir, )
def entrance(input_path='/mnt/chjinche/data/small/',
             output_path='/mnt/chjinche/data/image_dir/'):
    logger.info('Start!')
    # Case 1: input path is torchvision ImageFolder
    loader_dir = FolderBasedImageDirectory.load_organized(input_path)
    loader_dir.dump(output_path)
    logger.info('Finished')
Ejemplo n.º 4
0
 def apply(self, ports={}, params={}):
     input_image_dir = ports.get('Input image directory', None)
     logger.info(f'Applying transform:')
     transformed_dir = input_image_dir.apply_to_images(
         transform=lambda image: self.unloader(
             self.transform(image).squeeze(0)))
     return transformed_dir
Ejemplo n.º 5
0
    def onstart(self, ports={}, params={}):
        mode = params.get('Mode', None)
        input_transform_dir = ports.get('Input image transformation', None)
        self.transform = self.get_transforms(input_transform_dir, mode)
        logger.info(f'{mode}, transforms {self.transform}.')

        logger.info("Transformation init finished.")
def entrance(input_path='../image_dataset/', output_path='../image_dir/'):
    logger.info('Start!')
    # Case 1: input path is torchvision ImageFolder
    # TODO: Case 2: input path is custom image format
    loader_dir = FolderBasedImageDirectory.load_organized(input_path)
    loader_dir.dump(output_path)
    logger.info('Finished')
def entrance(src_path='../image_dir/',
             fraction=0.9,
             tgt_train_path='../image_dir_train/',
             tgt_test_path='../image_dir_test/'):
    logger.info('Start!')
    split_images(src_path, tgt_train_path, tgt_test_path, fraction)
    logger.info('Finished')
def entrance(
        src_path='/mnt/chjinche/test_data/detection/image_dir/',
        fraction=0.9,
        tgt_train_path='/mnt/chjinche/test_data/detection/image_dir_train/',
        tgt_test_path='/mnt/chjinche/test_data/detection/image_dir_test/'):
    logger.info('Start!')
    split_images(src_path, tgt_train_path, tgt_test_path, fraction)
    logger.info('Finished')
 def __init__(self, input_transform_path, transform_type):
     self.transform = self.get_transforms(input_transform_path,
                                          transform_type)
     logger.info(
         f'Set transform_type {transform_type}, transforms {self.transform}.'
     )
     self.unloader = transforms.ToPILImage()
     logger.info("Transformation init finished.")
Ejemplo n.º 10
0
def entrance(resize_size=256,
             center_crop_size=224,
             five_crop=False,
             ten_crop=False,
             pad=False,
             color_jitter=False,
             grayscale=False,
             random_crop=False,
             random_horizontal_flip=True,
             random_vertical_flip=False,
             random_resized_crop=False,
             random_rotation=False,
             random_affine=False,
             random_grayscale=False,
             random_perspective=False,
             random_erasing=False,
             normalize=True,
             output_path='../init_transform/'):
    # Construct image transform
    # TODO: check transforms ordering
    img_trans_dir = ImageTransformationDirectory.create(
        transforms=[('Resize', resize_size), ('CenterCrop', center_crop_size)])
    if five_crop:
        img_trans_dir.append('FiveCrop')
    if ten_crop:
        img_trans_dir.append('TenCrop')
    if pad:
        img_trans_dir.append('Pad')
    if color_jitter:
        img_trans_dir.append('ColorJitter')
    if grayscale:
        img_trans_dir.append('Grayscale')
    if random_crop:
        img_trans_dir.append('RandomCrop')
    if random_horizontal_flip:
        img_trans_dir.append('RandomHorizontalFlip')
    if random_vertical_flip:
        img_trans_dir.append('RandomVerticalFlip')
    if random_resized_crop:
        img_trans_dir.append('RandomResizedCrop')
    if random_rotation:
        img_trans_dir.append('RandomRotation')
    if random_affine:
        img_trans_dir.append('RandomAffine')
    if random_grayscale:
        img_trans_dir.append('RandomGrayscale')
    if random_perspective:
        img_trans_dir.append('RandomPerspective')
    if random_erasing:
        img_trans_dir.append('RandomErasing')
    # Need to do 'ToTensor' op ahead of normalzation.
    img_trans_dir.append('ToTensor')
    if normalize:
        img_trans_dir.append_normalize()
    logger.info(f'Constructed image transforms: {img_trans_dir.transforms}')
    # Dump
    img_trans_dir.dump(output_path)
    logger.info('Finished')
def entrance(input_path='../image_dataset/', output_path='../image_dir/'):
    logger.info('Start!')
    with TimeProfile(f"Mount/Download dataset to {input_path}"):
        print_dir_hierarchy_to_log(input_path)
    # Case 1: input path is torchvision ImageFolder
    # TODO: Case 2: input path is custom image format
    loader_dir = FolderBasedImageDirectory.load_organized(input_path)
    loader_dir.dump(output_path)
    logger.info('Finished.')
def get_split_list(ann_type, lst, fraction):
    n = len(lst)
    if ann_type in {ImageAnnotationTypeName.OBJECT_DETECTION}:
        train_idx, test_idx = train_test_split(list(range(n)),
                                               train_size=fraction,
                                               random_state=42)
    else:
        labels = [d['category_id'] for d in lst]
        train_idx, test_idx, train_label, test_label = train_test_split(
            list(range(n)), labels, stratify=labels, train_size=fraction)

    logger.info(f'train idx: {train_idx}.')
    logger.info(f'test idx: {test_idx}.')
    return train_idx, test_idx
Ejemplo n.º 13
0
def entrance(mode,
             input_transform_path='/mnt/chjinche/test_data/init_transform/',
             input_image_path='/mnt/chjinche/test_data/image_dir_test/',
             output_path='/mnt/chjinche/test_data/transform_test/'):
    params = {'Mode': mode}
    ports = {
        'Input image transformation':
        ImageTransformationDirectory.load(input_transform_path),
        'Input image directory':
        ImageDirectory.load(input_image_path)
    }
    task = ApplyImageTransformation()
    task.onstart(ports=ports, params=params)
    task.apply(ports=ports, params=params).dump(output_path)
    logger.info("Transformed dir dumped")
Ejemplo n.º 14
0
def evaluate(model, loader, print_freq=1, is_test=False):
    batch_time = AverageMeter()
    losses = AverageMeter()
    error = AverageMeter()
    # Model on eval mode
    model.eval()
    end = time.time()
    target_list = []
    pred_top1_list = []
    with torch.no_grad():
        for batch_idx, (input, target) in enumerate(loader):
            # Create variables
            if torch.cuda.is_available():
                input = input.cuda()
                target = target.cuda()
            # compute output
            output = model(input)
            loss = torch.nn.functional.cross_entropy(output, target)
            # measure accuracy and record loss
            batch_size = target.size(0)
            _, pred = output.data.cpu().topk(1, dim=1)
            target_list += target.tolist()
            pred_top1_list += [i[0] for i in pred.tolist()]
            error.update(
                torch.ne(pred.squeeze(), target.cpu()).float().sum().item() /
                batch_size, batch_size)
            losses.update(loss.item() / batch_size, batch_size)
            # measure elapsed time
            batch_time.update(time.time() - end)
            end = time.time()
            # print stats
            if batch_idx % print_freq == 0:
                res = '\t'.join([
                    'Test' if is_test else 'Valid',
                    'Iter: [{:d}/{:d}]'.format(batch_idx + 1, len(loader)),
                    'Avg_Time_Batch/Avg_Time_Epoch: {:.3f}/{:.3f}'.format(
                        batch_time.val, batch_time.avg),
                    'Avg_Loss_Batch/Avg_Loss_Epoch: {:.4f}/{:.4f}'.format(
                        losses.val, losses.avg),
                    'Avg_Error_Batch/Avg_Error_Epoch: {:.4f}/{:.4f}'.format(
                        error.val, error.avg),
                ])
                logger.info(res)
    # Return summary statistics
    return batch_time.avg, losses.avg, error.avg, (target_list, pred_top1_list)
def entrance(
        mode,
        input_transform_path='/mnt/chjinche/test_data/detection/init_transform/',
        input_image_path='/mnt/chjinche/test_data/detection/image_dir/',
        output_path='/mnt/chjinche/test_data/detection/transform/'):
    kwargs = {
        'mode':
        mode,
        'input_image_transformation':
        ImageTransformationDirectory.load(input_transform_path),
        'input_image_directory':
        ImageDirectory.load(input_image_path)
    }
    task = ApplyImageTransformation()
    task.on_init(**kwargs)
    output_dir, = task.run(**kwargs)
    output_dir.dump(output_path)
    logger.info("Transformed dir dumped")
Ejemplo n.º 16
0
def split_images(src_path, tgt_train_path, tgt_test_path, fraction):
    loaded_dir = ImageDirectory.load(src_path)
    lst = loaded_dir.image_lst
    logger.info(f'Start splitting.')
    train_set_lst, test_set_lst = get_stratified_split_list(lst, fraction)
    logger.info(f'Got stratified split list. train {len(train_set_lst)}, test {len(test_set_lst)}.')
    train_set_dir = FolderBasedImageDirectory.create_with_lst(src_path, train_set_lst)
    test_set_dir = FolderBasedImageDirectory.create_with_lst(src_path, test_set_lst)
    logger.info('Dump train set.')
    train_set_dir.dump(tgt_train_path)
    logger.info('Dump test set.')
    test_set_dir.dump(tgt_test_path)
def split_images(src_path, tgt_train_path, tgt_test_path, fraction):
    # TODO: use multi-label stratified split
    # from skmultilearn.model_selection import iterative_train_test_split
    # X_train, y_train, X_test, y_test = iterative_train_test_split(X, y, test_size = 0.5)
    loaded_dir = ImageDirectory.load(src_path)
    ann_type = loaded_dir.get_annotation_type()
    logger.info(f'task: {ann_type}')
    lst = loaded_dir.image_lst
    logger.info(f'Start splitting.')
    train_set_idx, test_set_idx = get_split_list(ann_type, lst, fraction)
    logger.info(
        f'Got split list. train {len(train_set_idx)}, test {len(test_set_idx)}.'
    )
    train_set_dir = loaded_dir.get_sub_dir(train_set_idx)
    test_set_dir = loaded_dir.get_sub_dir(test_set_idx)
    logger.info('Dump train set.')
    train_set_dir.dump(tgt_train_path)
    logger.info('Dump test set.')
    test_set_dir.dump(tgt_test_path)
Ejemplo n.º 18
0
 def train_one_epoch(self, loader, optimizer, epoch, epochs, print_freq=1):
     batch_time = AverageMeter()
     losses = AverageMeter()
     error = AverageMeter()
     # Model on train mode
     # print(self.model)
     self.model.train()
     end = time.time()
     batches = len(loader)
     for batch_idx, (input, target) in enumerate(loader):
         # Create variables
         if torch.cuda.is_available():
             input = input.cuda()
             target = target.cuda()
         # Compute output
         output = self.model(input)
         loss = torch.nn.functional.cross_entropy(output, target)
         # Measure accuracy and record loss
         batch_size = target.size(0)
         _, pred = output.data.cpu().topk(1, dim=1)
         error.update(
             torch.ne(pred.squeeze(), target.cpu()).float().sum().item() /
             batch_size, batch_size)
         losses.update(loss.item(), batch_size)
         # Compute gradient and do SGD step
         optimizer.zero_grad()
         loss.backward()
         optimizer.step()
         # Measure elapsed time
         batch_time.update(time.time() - end)
         end = time.time()
         if batch_idx % print_freq == 0:
             res = '\t'.join([
                 f'Epoch: [{epoch + 1}/{epochs}]',
                 f'Iter: [{batch_idx + 1}/{batches}]',
                 f'Avg_Time_Batch/Avg_Time_Epoch: {batch_time.val:.3f}/{batch_time.avg:.3f}',
                 f'Avg_Loss_Batch/Avg_Loss_Epoch: {losses.val:.4f}/{losses.avg:.4f}',
                 f'Avg_Error_Batch/Avg_Error_Epoch: {error.val:.4f}/{error.avg:.4f}'
             ])
             logger.info(res)
     # Return summary statistics
     return batch_time.avg, losses.avg, error.avg
Ejemplo n.º 19
0
def split_images(src_path, tgt_train_path, tgt_test_path, fraction):
    loaded_dir = ImageDirectory.load(src_path)
    lst = loaded_dir.image_lst
    logger.info(f'Start splitting.')
    train_set_idx, test_set_idx = get_stratified_split_list(lst, fraction)
    logger.info(
        f'Got stratified split list. train {len(train_set_idx)}, test {len(test_set_idx)}.'
    )
    train_set_dir = loaded_dir.get_sub_dir(train_set_idx)
    test_set_dir = loaded_dir.get_sub_dir(test_set_idx)
    logger.info('Dump train set.')
    train_set_dir.dump(tgt_train_path)
    logger.info('Dump test set.')
    test_set_dir.dump(tgt_test_path)
Ejemplo n.º 20
0
 def __init__(self,
              model_type='densenet201',
              pretrained=True,
              memory_efficient=False,
              num_classes=20):
     logger.info('Init DenseNet.')
     super(DenseNet, self).__init__()
     if not pretrained:
         model_type = "densenet201"
     densenet_func = getattr(densenet, model_type, None)
     if densenet_func is None:
         # todo: catch exception and throw AttributeError
         logger.info(f"Error: No such pretrained model {model_type}")
         sys.exit()
     logger.info(f"Model type {model_type}, pretrained {pretrained}")
     self.model1 = densenet_func(pretrained=pretrained)
     # Pretrained model is trained based on 1000-class ImageNet dataset
     self.model2 = nn.Linear(1000, num_classes)
     logger.info(f"Model init finished")
Ejemplo n.º 21
0
def entrance(save_model_path='/mnt/chjinche/test_data/detection/init_model',
             model_type='fasterrcnn_resnet50_fpn',
             pretrained=True):
    model_config = {
        'model_class': 'FasterRCNN',
        'model_type': model_type,
        'pretrained': pretrained
    }
    logger.info('Dump untrained model.')
    logger.info(f'Model config: {model_config}.')
    dumper = pickle_dumper(model_config, 'model_config.pkl')
    save_model_to_directory(save_model_path, dumper)
    logger.info('Finished.')
Ejemplo n.º 22
0
def entrance(
        save_model_path='/mnt/chjinche/projects/saved_untrained_model_resnet',
        model_type='resnext101_32x8d',
        pretrained=True):
    model_config = {
        'model_class': 'ResNet',
        'model_type': model_type,
        'pretrained': pretrained
    }
    logger.info('Dump untrained model.')
    logger.info(f'Model config: {model_config}.')
    dumper = pickle_dumper(model_config, 'model_config.pkl')
    save_model_to_directory(save_model_path, dumper)
    logger.info('Finished.')
Ejemplo n.º 23
0
def entrance(save_model_path='../init_model',
             model_type='densenet201',
             pretrained=True,
             memory_efficient=False):
    model_config = {
        'model_class': 'DenseNet',
        'model_type': model_type,
        'pretrained': pretrained,
        'memory_efficient': memory_efficient
    }
    logger.info('Dump untrained model.')
    logger.info(f'Model config: {model_config}.')
    dumper = pickle_dumper(model_config, 'model_config.pkl')
    save_model_to_directory(save_model_path, dumper)
    logger.info('Finished.')
Ejemplo n.º 24
0
def entrance(
        input_path='/mnt/chjinche/test_data/classification/compressed/image_dataset.zip',
        output_path='/mnt/chjinche/test_data/test/image_dir/'):
    logger.info('Start!')
    logger.info(f'input path {input_path}')
    # TODO:Case 1: input path is torchvision ImageFolder
    # loader_dir = FolderBasedImageDirectory.load_organized(input_path)
    # Case 2: input path is compressed file
    compressed_extensions = {'.tar', '.zip'}
    compressed_path = None
    if Path(input_path).is_file():
        compressed_path = input_path
    else:
        for path in Path(input_path).glob(r'**/*'):
            print(path)
            if path.suffix in compressed_extensions:
                compressed_path = path

    logger.info(f'compressed file path {compressed_path}')
    loader_dir = ImageDirectory.load_compressed(compressed_path)
    # TODO: Case 3: input path is custom directory
    loader_dir.dump(output_path)
    logger.info('Finished.')
Ejemplo n.º 25
0
    def fit(self,
            train_set,
            valid_set,
            epochs,
            batch_size,
            lr=0.001,
            wd=0.0001,
            momentum=0.9,
            random_seed=None,
            patience=10):
        logger.info('Torch cuda random seed setting.')
        # Torch cuda random seed setting
        if random_seed is not None:
            if torch.cuda.is_available():
                if torch.cuda.device_count() > 1:
                    torch.cuda.manual_seed_all(random_seed)
                else:
                    torch.cuda.manual_seed(random_seed)
            else:
                torch.manual_seed(random_seed)
        logger.info("Data start loading.")
        # DataLoader
        train_loader = torch.utils.data.DataLoader(
            train_set,
            batch_size=batch_size,
            shuffle=True,
            pin_memory=(torch.cuda.is_available()),
            num_workers=0)
        valid_loader = torch.utils.data.DataLoader(
            valid_set,
            batch_size=batch_size,
            shuffle=False,
            pin_memory=(torch.cuda.is_available()),
            num_workers=0)
        if torch.cuda.is_available():
            self.model = self.model.cuda()

        if torch.cuda.device_count() > 1:
            # self.model = torch.nn.parallel.DistributedDataParallel(self.model).cuda()
            self.model = torch.nn.DataParallel(self.model).cuda()

        optimizer = torch.optim.SGD(self.model.parameters(),
                                    lr=lr,
                                    momentum=momentum,
                                    nesterov=True,
                                    weight_decay=wd)
        scheduler = torch.optim.lr_scheduler.MultiStepLR(
            optimizer, milestones=[0.5 * epochs, 0.75 * epochs], gamma=0.1)
        logger.info('Start training epochs.')
        best_error = 1
        counter = 0
        for epoch in range(epochs):
            _, train_loss, train_error = self.train_one_epoch(
                loader=train_loader,
                optimizer=optimizer,
                epoch=epoch,
                epochs=epochs)
            scheduler.step(epoch=epoch)
            _, valid_loss, valid_error, _ = evaluate(model=self.model,
                                                     loader=valid_loader)
            # Determine if model is the best
            if valid_error < best_error:
                is_best = True
                best_error = valid_error
            else:
                is_best = False

            # Early stop
            last_epoch_valid_loss = 0
            if epoch == 0:
                last_epoch_valid_loss = valid_loss
            else:
                if valid_loss >= last_epoch_valid_loss:
                    counter += 1
                else:
                    counter = 0
                last_epoch_valid_loss = valid_loss

            logger.info(
                f'valid loss did not decrease consecutively for {counter} epoch'
            )
            # TODO: save checkpoint files, but removed now to increase web service deployment efficiency.
            logger.info(','.join([
                f'Epoch {epoch + 1:d}', f'train_loss {train_loss:.6f}',
                f'train_error {train_error:.6f}',
                f'valid_loss {valid_loss:.5f}',
                f'valid_error {valid_error:.5f}'
            ]))
            if is_best:
                logger.info(
                    # f'Get better top1 accuracy: {1-best_error:.4f} will saving weights to {best_checkpoint_name}'
                    f'Get better top1 accuracy: {1-best_error:.4f}, best checkpoint will be updated.'
                )

            early_stop = True if counter >= patience else False
            if early_stop:
                logger.info("Early stopped.")
                break
Ejemplo n.º 26
0
    def __init__(self, **kwargs):
        super().__init__()
        self.kwargs = kwargs.copy()
        self.pretrained = kwargs.get('pretrained', None)
        # TODO: error if pretrained is None
        self.model_type = kwargs.get('model_type', None)
        logger.info(f'Model config {kwargs}.')
        kwargs.pop('model_type', None)
        logger.info(f'Init {self.model_type}.')
        model_func = getattr(models, self.model_type, None)
        if model_func is None:
            # TODO: catch exception and throw AttributeError
            logger.info(f"Error: No such pretrained model {self.model_type}")
            sys.exit()

        if self.pretrained:
            # Drop 'num_classes' para to avoid size mismatch
            kwargs.pop('num_classes', None)
            logger.info(f'Model config {kwargs}.')
            self.model = model_func(**kwargs)
        else:
            logger.info(f'Model config {kwargs}.')
            self.model = model_func(**kwargs)

        logger.info(f"Model init finished, {self.model}.")
def entrance(input_model_path='../init_model',
             train_data_path='../transform_train/',
             valid_data_path='../transform_test/',
             save_model_path='../saved_model',
             epochs=20,
             batch_size=16,
             learning_rate=0.001,
             random_seed=231,
             patience=2):
    logger.info("Start training.")
    logger.info(f"data path: {train_data_path}")
    logger.info(f"data path: {valid_data_path}")
    train_set = ImageDirectory.load(train_data_path).to_torchvision_dataset()
    logger.info(f"Training classes: {train_set.classes}")
    valid_set = ImageDirectory.load(valid_data_path).to_torchvision_dataset()
    # TODO: assert the same classes between train_set and valid_set.
    logger.info("Made dataset")
    classes = train_set.classes
    num_classes = len(classes)
    # TODO: use image directory api to get id-to-class mapping.
    id_to_class_dict = {i: classes[i] for i in range(num_classes)}
    logger.info("Start building model.")
    model_config = load_model_from_directory(input_model_path,
                                             model_loader=pickle_loader).data
    model_class = getattr(modellib, model_config.get('model_class', None),
                          None)
    logger.info(f'Model class: {model_class}.')
    model_config.pop('model_class', None)
    model_config['num_classes'] = num_classes
    logger.info(f'Model_config: {model_config}.')
    model = model_class(**model_config)
    logger.info("Built model. Start training.")
    model = train(model=model,
                  train_set=train_set,
                  valid_set=valid_set,
                  epochs=epochs,
                  batch_size=batch_size,
                  lr=learning_rate,
                  random_seed=random_seed,
                  patience=patience)
    # Save model file, configs and install dependencies
    # TODO: designer.model could support pathlib.Path
    conda = {
        "dependencies": [{
            "pip": [
                "azureml-defaults",
                "azureml-designer-core[image]==0.0.25.post7829218",
                "fire==0.1.3",
                "git+https://github.com/StudioCommunity/CustomModules-1.git@master#subdirectory=azureml-custom-module-examples/image-classification",
                "--extra-index-url=https://azureml-modules:3nvdtawseij7o2oenxojj35c43i5lu2ucf77pugohh4g5eqn6xnq@msdata.pkgs.visualstudio.com/_packaging/azureml-modules%40Local/pypi/simple/"
            ]
        }]
    }
    logger.info(f"Saving with conda: {conda}")
    save_pytorch_state_dict_model(model,
                                  init_params=model_config,
                                  path=save_model_path,
                                  task_type=TaskType.MultiClassification,
                                  label_map=id_to_class_dict,
                                  conda=conda)
    logger.info('This experiment has been completed.')
Ejemplo n.º 28
0
def entrance(train_data_path='/mnt/chjinche/data/out_transform_train/',
             valid_data_path='/mnt/chjinche/data/out_transform_test/',
             save_model_path='/mnt/chjinche/projects/saved_model',
             model_type='densenet201',
             pretrained=True,
             memory_efficient=False,
             epochs=1,
             batch_size=16,
             learning_rate=0.001,
             random_seed=231,
             patience=2):
    logger.info("Start training.")
    logger.info(f"data path: {train_data_path}")
    logger.info(f"data path: {valid_data_path}")
    train_set = ImageDirectory.load(train_data_path).to_torchvision_dataset()
    logger.info(f"Training classes: {train_set.classes}")
    valid_set = ImageDirectory.load(valid_data_path).to_torchvision_dataset()
    # assert the same classes between train_set and valid_set.
    logger.info("Made dataset")
    classes = train_set.classes
    num_classes = len(classes)
    # TODO: use image directory api to get id-to-class mapping.
    id_to_class_dict = {i: classes[i] for i in range(num_classes)}
    logger.info("Start constructing model")
    model_config = {
        'model_type': model_type,
        'pretrained': pretrained,
        'memory_efficient': memory_efficient,
        'num_classes': num_classes
    }
    model = DenseNet(**model_config)
    model = train(model=model,
                  train_set=train_set,
                  valid_set=valid_set,
                  epochs=epochs,
                  batch_size=batch_size,
                  lr=learning_rate,
                  random_seed=random_seed,
                  patience=patience)
    # Save model file, configs and install dependencies
    # TODO: designer.model could support pathlib.Path
    conda = {
        "dependencies": [{
            "pip": [
                "azureml-defaults",
                "azureml-designer-core[image]==0.0.25.post7829218",
                "fire==0.1.3",
                "git+https://github.com/StudioCommunity/CustomModules-1.git@master#subdirectory=azureml-custom-module-examples/image-classification",
                "--extra-index-url=https://azureml-modules:3nvdtawseij7o2oenxojj35c43i5lu2ucf77pugohh4g5eqn6xnq@msdata.pkgs.visualstudio.com/_packaging/azureml-modules%40Local/pypi/simple/"
            ]
        }]
    }
    save_pytorch_state_dict_model(model,
                                  init_params=model_config,
                                  path=save_model_path,
                                  task_type=TaskType.MultiClassification,
                                  label_map=id_to_class_dict,
                                  conda=conda)
    logger.info('This experiment has been completed.')
Ejemplo n.º 29
0
    def fit(self,
            train_set,
            valid_set,
            epochs,
            batch_size,
            lr=0.001,
            wd=0.0001,
            momentum=0.9,
            random_seed=None,
            patience=10):
        logger.info('Torch cuda random seed setting.')
        # Torch cuda random seed setting
        if random_seed is not None:
            if torch.cuda.is_available():
                if torch.cuda.device_count() > 1:
                    torch.cuda.manual_seed_all(random_seed)
                else:
                    torch.cuda.manual_seed(random_seed)
            else:
                torch.manual_seed(random_seed)
        logger.info("Data start loading.")
        # DataLoader
        # train_set = remove_images_without_annotations(train_set)
        train_loader = torch.utils.data.DataLoader(
            train_set,
            batch_size=batch_size,
            shuffle=True,
            collate_fn=utils.collate_fn,
            pin_memory=(torch.cuda.is_available()),
            num_workers=0)
        valid_loader = torch.utils.data.DataLoader(
            valid_set,
            batch_size=batch_size,
            shuffle=False,
            collate_fn=utils.collate_fn,
            pin_memory=(torch.cuda.is_available()),
            num_workers=0)
        if torch.cuda.is_available():
            self.model = self.model.cuda()

        if torch.cuda.device_count() > 1:
            # self.model = torch.nn.parallel.DistributedDataParallel(self.model).cuda()
            self.model = torch.nn.DataParallel(self.model).cuda()

        # reduce learning rate every step_size epochs by a factor of gamma (by default) 0.1.
        step_size = None
        if step_size is None:
            step_size = int(np.round(epochs / 1.5))

        self.device = torch_device()
        # construct our optimizer
        params = [p for p in self.model.parameters() if p.requires_grad]
        self.optimizer = torch.optim.SGD(
            params, lr=lr, momentum=momentum, weight_decay=wd
        )

        # and a learning rate scheduler
        self.lr_scheduler = torch.optim.lr_scheduler.StepLR(
            self.optimizer, step_size=step_size, gamma=0.1
        )

        # store data in these arrays to plot later
        self.losses = []
        self.ap = []
        self.ap_iou_point_5 = []

        # main training loop
        self.epochs = epochs
        for epoch in range(self.epochs):

            # train for one epoch, printing every 10 iterations
            logger_per_epoch = train_one_epoch(
                self.model,
                self.optimizer,
                train_loader,
                self.device,
                epoch,
                print_freq=10,
            )
            self.losses.append(logger_per_epoch.meters["loss"].median)

            # update the learning rate
            self.lr_scheduler.step(epoch=epoch)

            # evaluate
            e = evaluate(self.model, valid_loader, self.device)
            self.ap.append(_calculate_ap(e))
            self.ap_iou_point_5.append(_calculate_ap(e, iou_threshold_idx=0))
Ejemplo n.º 30
0
 def __init__(self, **kwargs):
     super().__init__(**kwargs)
     self.update_nn()
     logger.info(f"Model init finished, {self.model}.")