Exemplo n.º 1
0
def main():
    args, arg_groups = ArgumentParser(mode='generate').parse()

    #Creating the target directory name
    name = ''
    if args.sourcepath[-1] == '/':
        name = os.path.basename(args.sourcepath[0:-1]) + '/'
    elif args.sourcepath[-1] != '/':
        name = os.path.basename(args.sourcepath) + '/'

    data_directory = './datasets/' + name + 'TrainVal/'

    #Scenario depending on filetype (img/h5/vid)
    if args.datatype == 'h5':
        h5_files = list_files(args.sourcepath, 'h5')
        extract_frames_h5(h5_files[0],
                          args.sourcepath + 'frames/',
                          channel=args.h5_channels)
        source = args.sourcepath + 'frames/'
        extension = '.jpg'

    elif args.datatype == 'video':

        extract_frames_video(args.sourcepath, args.extension)
        extension = '.jpg'
        source = args.sourcepath + 'frames/'

    elif args.datatype == 'image':
        extension = args.extension
        source = args.sourcepath

    shutil.copytree(source, data_directory)

    if args.augment != 0:
        augment_images(data_directory,
                       someAug(),
                       times_target=args.augment,
                       source=True)

    create_csv_split(data_directory)
Exemplo n.º 2
0
from image.normalization import NormalizeImageDict
from util.torch_util import save_checkpoint, str_to_bool
import numpy as np
import numpy.random
from collections import OrderedDict
from options.options import ArgumentParser
"""

Script to train the model as presented in the CNNGeometric CVPR'17 paper
using synthetically warped image pairs and strong supervision

"""
print('CNNGeometric training script using strong supervision')

# Argument parsing
args, arg_groups = ArgumentParser(mode='train_strong').parse()
print(args)

# Seed and CUDA
use_cuda = torch.cuda.is_available()
torch.manual_seed(args.seed)
if use_cuda:
    torch.cuda.manual_seed(args.seed)
np.random.seed(args.seed)

# Download dataset if needed and set paths
if args.training_dataset == 'pascal':
    if args.dataset_image_path == '':
        if not exists('datasets/pascal-voc11/TrainVal'):
            download_pascal('datasets/pascal-voc11/')
        args.dataset_image_path = 'datasets/pascal-voc11/'
Exemplo n.º 3
0
from collections import OrderedDict
from options.options import ArgumentParser
from util.dataloader import default_collate
from util.torch_util import collate_custom

"""

Script to evaluate a trained model as presented in the CNNGeometric CVPR'17 paper
on the ProposalFlow/Caltech-101 dataset

"""

print('WeakAlign evaluation script')

# Argument parsing
args,arg_groups = ArgumentParser(mode='eval').parse()
print(args)

torch.cuda.set_device(args.gpu)

# check provided models and deduce if single/two-stage model should be used
do_aff = args.model_aff!=""
do_tps = args.model_tps!=""
two_stage = args.model!='' or (do_aff and do_tps)

if args.eval_dataset_path=='' and args.eval_dataset=='pf':
    args.eval_dataset_path='datasets/proposal-flow-willow/'

if args.eval_dataset_path=='' and args.eval_dataset=='pf_pascal':
    args.eval_dataset_path='datasets/proposal-flow-pascal/'
Exemplo n.º 4
0
def main():

    args, arg_groups = ArgumentParser(mode='train').parse()
    print(args)

    use_cuda = torch.cuda.is_available()
    device = torch.device('cuda') if use_cuda else torch.device('cpu')
    # Seed
    torch.manual_seed(args.seed)
    if use_cuda:
        torch.cuda.manual_seed(args.seed)

    # Download dataset if needed and set paths
    if args.training_dataset == 'pascal':

        if args.dataset_image_path == '' and not os.path.exists(
                'datasets/pascal-voc11/TrainVal'):
            download_pascal('datasets/pascal-voc11/')

        if args.dataset_image_path == '':
            args.dataset_image_path = 'datasets/pascal-voc11/'

        args.dataset_csv_path = 'training_data/pascal-random'

    # CNN model and loss
    print('Creating CNN model...')
    if args.geometric_model == 'affine':
        cnn_output_dim = 6
    elif args.geometric_model == 'hom' and args.four_point_hom:
        cnn_output_dim = 8
    elif args.geometric_model == 'hom' and not args.four_point_hom:
        cnn_output_dim = 9
    elif args.geometric_model == 'tps':
        cnn_output_dim = 18

    model = CNNGeometric(use_cuda=use_cuda,
                         output_dim=cnn_output_dim,
                         **arg_groups['model'])

    if args.geometric_model == 'hom' and not args.four_point_hom:
        init_theta = torch.tensor([1, 0, 0, 0, 1, 0, 0, 0, 1], device=device)
        model.FeatureRegression.linear.bias.data += init_theta

    if args.geometric_model == 'hom' and args.four_point_hom:
        init_theta = torch.tensor([-1, -1, 1, 1, -1, 1, -1, 1], device=device)
        model.FeatureRegression.linear.bias.data += init_theta

    if args.use_mse_loss:
        print('Using MSE loss...')
        loss = nn.MSELoss()
    else:
        print('Using grid loss...')
        loss = TransformedGridLoss(use_cuda=use_cuda,
                                   geometric_model=args.geometric_model)

    # Initialize Dataset objects
    dataset = SynthDataset(geometric_model=args.geometric_model,
                           dataset_csv_path=args.dataset_csv_path,
                           dataset_csv_file='train.csv',
                           dataset_image_path=args.dataset_image_path,
                           transform=NormalizeImageDict(['image']),
                           random_sample=args.random_sample)

    dataset_val = SynthDataset(geometric_model=args.geometric_model,
                               dataset_csv_path=args.dataset_csv_path,
                               dataset_csv_file='val.csv',
                               dataset_image_path=args.dataset_image_path,
                               transform=NormalizeImageDict(['image']),
                               random_sample=args.random_sample)

    # Set Tnf pair generation func
    pair_generation_tnf = SynthPairTnf(geometric_model=args.geometric_model,
                                       use_cuda=use_cuda)

    # Initialize DataLoaders
    dataloader = DataLoader(dataset,
                            batch_size=args.batch_size,
                            shuffle=True,
                            num_workers=4)

    dataloader_val = DataLoader(dataset_val,
                                batch_size=args.batch_size,
                                shuffle=True,
                                num_workers=4)

    # Optimizer and eventual scheduler
    optimizer = optim.Adam(model.FeatureRegression.parameters(), lr=args.lr)

    if args.lr_scheduler:
        scheduler = torch.optim.lr_scheduler.CosineAnnealingLR(
            optimizer, T_max=args.lr_max_iter, eta_min=1e-6)
        # scheduler = torch.optim.lr_scheduler.ReduceLROnPlateau(optimizer, 'min')
    else:
        scheduler = False

    # Train

    # Set up names for checkpoints
    if args.use_mse_loss:
        ckpt = args.trained_model_fn + '_' + args.geometric_model + '_mse_loss' + args.feature_extraction_cnn
        checkpoint_path = os.path.join(args.trained_model_dir,
                                       args.trained_model_fn,
                                       ckpt + '.pth.tar')
    else:
        ckpt = args.trained_model_fn + '_' + args.geometric_model + '_grid_loss' + args.feature_extraction_cnn
        checkpoint_path = os.path.join(args.trained_model_dir,
                                       args.trained_model_fn,
                                       ckpt + '.pth.tar')
    if not os.path.exists(args.trained_model_dir):
        os.mkdir(args.trained_model_dir)

    # Set up TensorBoard writer
    if not args.log_dir:
        tb_dir = os.path.join(args.trained_model_dir,
                              args.trained_model_fn + '_tb_logs')
    else:
        tb_dir = os.path.join(args.log_dir, args.trained_model_fn + '_tb_logs')

    logs_writer = SummaryWriter(tb_dir)
    # add graph, to do so we have to generate a dummy input to pass along with the graph
    dummy_input = {
        'source_image': torch.rand([args.batch_size, 3, 240, 240],
                                   device=device),
        'target_image': torch.rand([args.batch_size, 3, 240, 240],
                                   device=device),
        'theta_GT': torch.rand([16, 2, 3], device=device)
    }

    logs_writer.add_graph(model, dummy_input)

    # Start of training
    print('Starting training...')

    best_val_loss = float("inf")

    for epoch in range(1, args.num_epochs + 1):

        # we don't need the average epoch loss so we assign it to _
        _ = train(epoch,
                  model,
                  loss,
                  optimizer,
                  dataloader,
                  pair_generation_tnf,
                  log_interval=args.log_interval,
                  scheduler=scheduler,
                  tb_writer=logs_writer)

        val_loss = validate_model(model, loss, dataloader_val,
                                  pair_generation_tnf, epoch, logs_writer)

        # remember best loss
        is_best = val_loss < best_val_loss
        best_val_loss = min(val_loss, best_val_loss)
        save_checkpoint(
            {
                'epoch': epoch + 1,
                'args': args,
                'state_dict': model.state_dict(),
                'best_val_loss': best_val_loss,
                'optimizer': optimizer.state_dict(),
            }, is_best, checkpoint_path)

    logs_writer.close()
    print('Done!')
Exemplo n.º 5
0
def main():
    #Parsing args
    args, arg_groups = ArgumentParser(mode='run').parse()
    print("Running script")
    use_cuda = torch.cuda.is_available()
    device = torch.device('cuda') if use_cuda else torch.device('cpu')
    
    ### Loading the model ###
    
    #Parse args for network params (weights and models) and sets the feature regressor accordingly for the pretrained weights.
    aff_split = os.path.dirname(args.aff_weight).split('/trained_models/')[-1].split('_')
    tps_split = os.path.dirname(args.tps_weight).split('/trained_models/')[-1].split('_')
    feat_reg = [args.aff_fr, args.tps_fr]
    
    #Checking if the pathnames contains keyword to infer the model type (FE + FR)
    for index, split in enumerate([aff_split, tps_split]):
        if split[0] == 'baseline' or split[1] == 'basefr':
            feat_reg[index] = 'base'
            
        elif split[1] == 'deepfr':
            feat_reg[index] = 'deep'
            
        elif split[1] == 'simplerfr':
            feat_reg[index] = 'simpler'
            
    #Loading network
    model_aff, model_tps = load_model(args.aff_weight, args.aff_model, feat_reg[0],
                                     args.tps_weight, args.tps_model, feat_reg[1])
    
    #Image warping
    #In the case we specify datatype = video, but leave the default extension which is jpg:
    ext = args.extension
    if args.datatype == 'video' and args.extension == '.jpg':
    	ext = input("Please enter the extension of your video file. Ex : .mp4, .avi, .. \ninput :")
    
    if args.datatype=='image':
        savepath=batch_align(args.datapath, args.alignment_target, model_aff, model_tps, args.extension)
        save_video(savepath)
    
    elif args.datatype =='video': #first extracts all frames, then align
        extract_frames_video(args.datapath, ext)
        frames_path = args.datapath+'frames/'
        if args.alignment_target != '' and args.alignment_target != 'previous':
            target = frames_path+args.alignment_target+'.jpg'
        else:
            target = args.alignment_target
        savepath = batch_align(frames_path, target, model_aff, model_tps, '.jpg')
        save_video(savepath)
    
    elif args.datatype == 'h5': #assumes red and green channels with no blue channel, and datatype = int16 
        if args.datapath[-1]=='/':
            h5_file = h5.File(list_files(args.datapath,'h5'))
            frames_path = args.datapath+'/frames/'
            
        elif args.datapath[-3:] == '.h5':
            h5_file = h5.File(args.datapath)
            frames_path = os.path.dirname(args.datapath)+'/frames/'
            
        target = frames_path+args.alignment_target+'.jpg'
        extract_frames_h5(h5_file, frames_path, channel = args.h5_channels)
        savepath = batch_align(frames_path, target, model_aff, model_tps, '.jpg')
        save_video(savepath)
Exemplo n.º 6
0
def main():

    args, arg_groups = ArgumentParser(mode='train').parse()
    print(args)

    use_cuda = torch.cuda.is_available()
    use_me = args.use_me
    device = torch.device('cuda') if use_cuda else torch.device('cpu')
    # Seed
    # torch.manual_seed(args.seed)
    # if use_cuda:
    # torch.cuda.manual_seed(args.seed)

    # CNN model and loss
    print('Creating CNN model...')
    if args.geometric_model == 'affine_simple':
        cnn_output_dim = 3
    elif args.geometric_model == 'affine_simple_4':
        cnn_output_dim = 4
    else:
        raise NotImplementedError('Specified geometric model is unsupported')

    model = CNNGeometric(use_cuda=use_cuda,
                         output_dim=cnn_output_dim,
                         **arg_groups['model'])

    if args.geometric_model == 'affine_simple':
        init_theta = torch.tensor([0.0, 1.0, 0.0], device=device)
    elif args.geometric_model == 'affine_simple_4':
        init_theta = torch.tensor([0.0, 1.0, 0.0, 0.0], device=device)

    try:
        model.FeatureRegression.linear.bias.data += init_theta
    except:
        model.FeatureRegression.resnet.fc.bias.data += init_theta

    args.load_images = False
    if args.loss == 'mse':
        print('Using MSE loss...')
        loss = nn.MSELoss()
    elif args.loss == 'weighted_mse':
        print('Using weighted MSE loss...')
        loss = WeightedMSELoss(use_cuda=use_cuda)
    elif args.loss == 'reconstruction':
        print('Using reconstruction loss...')
        loss = ReconstructionLoss(
            int(np.rint(args.input_width * (1 - args.crop_factor) / 16) * 16),
            int(np.rint(args.input_height * (1 - args.crop_factor) / 16) * 16),
            args.input_height,
            use_cuda=use_cuda)
        args.load_images = True
    elif args.loss == 'combined':
        print('Using combined loss...')
        loss = CombinedLoss(args, use_cuda=use_cuda)
        if args.use_reconstruction_loss:
            args.load_images = True
    elif args.loss == 'grid':
        print('Using grid loss...')
        loss = SequentialGridLoss(use_cuda=use_cuda)
    else:
        raise NotImplementedError('Specifyed loss %s is not supported' %
                                  args.loss)

    # Initialize Dataset objects
    if use_me:
        dataset = MEDataset(geometric_model=args.geometric_model,
                            dataset_csv_path=args.dataset_csv_path,
                            dataset_csv_file='train.csv',
                            dataset_image_path=args.dataset_image_path,
                            input_height=args.input_height,
                            input_width=args.input_width,
                            crop=args.crop_factor,
                            use_conf=args.use_conf,
                            use_random_patch=args.use_random_patch,
                            normalize_inputs=args.normalize_inputs,
                            random_sample=args.random_sample,
                            load_images=args.load_images)

        dataset_val = MEDataset(geometric_model=args.geometric_model,
                                dataset_csv_path=args.dataset_csv_path,
                                dataset_csv_file='val.csv',
                                dataset_image_path=args.dataset_image_path,
                                input_height=args.input_height,
                                input_width=args.input_width,
                                crop=args.crop_factor,
                                use_conf=args.use_conf,
                                use_random_patch=args.use_random_patch,
                                normalize_inputs=args.normalize_inputs,
                                random_sample=args.random_sample,
                                load_images=args.load_images)

    else:

        dataset = SynthDataset(geometric_model=args.geometric_model,
                               dataset_csv_path=args.dataset_csv_path,
                               dataset_csv_file='train.csv',
                               dataset_image_path=args.dataset_image_path,
                               transform=NormalizeImageDict(['image']),
                               random_sample=args.random_sample)

        dataset_val = SynthDataset(geometric_model=args.geometric_model,
                                   dataset_csv_path=args.dataset_csv_path,
                                   dataset_csv_file='val.csv',
                                   dataset_image_path=args.dataset_image_path,
                                   transform=NormalizeImageDict(['image']),
                                   random_sample=args.random_sample)

    # Set Tnf pair generation func
    if use_me:
        pair_generation_tnf = BatchTensorToVars(use_cuda=use_cuda)
    elif args.geometric_model == 'affine_simple' or args.geometric_model == 'affine_simple_4':
        pair_generation_tnf = SynthPairTnf(geometric_model='affine',
                                           use_cuda=use_cuda)
    else:
        raise NotImplementedError('Specified geometric model is unsupported')

    # Initialize DataLoaders
    dataloader = DataLoader(dataset,
                            batch_size=args.batch_size,
                            shuffle=True,
                            num_workers=4)

    dataloader_val = DataLoader(dataset_val,
                                batch_size=args.batch_size,
                                shuffle=True,
                                num_workers=4)

    # Optimizer
    optimizer = optim.Adam(model.FeatureRegression.parameters(), lr=args.lr)

    # Train

    # Set up names for checkpoints
    ckpt = args.trained_model_fn + '_' + args.geometric_model + '_' + args.loss + '_loss_'
    checkpoint_path = os.path.join(args.trained_model_dir,
                                   args.trained_model_fn, ckpt + '.pth.tar')
    if not os.path.exists(args.trained_model_dir):
        os.mkdir(args.trained_model_dir)

    # Set up TensorBoard writer
    if not args.log_dir:
        tb_dir = os.path.join(args.trained_model_dir,
                              args.trained_model_fn + '_tb_logs')
    else:
        tb_dir = os.path.join(args.log_dir, args.trained_model_fn + '_tb_logs')

    logs_writer = SummaryWriter(tb_dir)
    # add graph, to do so we have to generate a dummy input to pass along with the graph
    if use_me:
        dummy_input = {
            'mv_L2R': torch.rand([args.batch_size, 2, 216, 384],
                                 device=device),
            'mv_R2L': torch.rand([args.batch_size, 2, 216, 384],
                                 device=device),
            'grid_L2R': torch.rand([args.batch_size, 2, 216, 384],
                                   device=device),
            'grid_R2L': torch.rand([args.batch_size, 2, 216, 384],
                                   device=device),
            'grid': torch.rand([args.batch_size, 2, 216, 384], device=device),
            'conf_L': torch.rand([args.batch_size, 1, 216, 384],
                                 device=device),
            'conf_R': torch.rand([args.batch_size, 1, 216, 384],
                                 device=device),
            'theta_GT': torch.rand([args.batch_size, 4], device=device),
        }
        if args.load_images:
            dummy_input['img_R_orig'] = torch.rand(
                [args.batch_size, 1, 216, 384], device=device)
            dummy_input['img_R'] = torch.rand([args.batch_size, 1, 216, 384],
                                              device=device)
    else:
        dummy_input = {
            'source_image':
            torch.rand([args.batch_size, 3, 240, 240], device=device),
            'target_image':
            torch.rand([args.batch_size, 3, 240, 240], device=device),
            'theta_GT':
            torch.rand([args.batch_size, 2, 3], device=device)
        }

    logs_writer.add_graph(model, dummy_input)

    # Start of training
    print('Starting training...')

    best_val_loss = float("inf")

    max_batch_iters = len(dataloader)
    print('Iterations for one epoch:', max_batch_iters)
    epoch_to_change_lr = int(args.lr_max_iter / max_batch_iters * 2 + 0.5)

    # Loading checkpoint
    model, optimizer, start_epoch, best_val_loss, last_epoch = load_checkpoint(
        checkpoint_path, model, optimizer, device)

    # Scheduler
    if args.lr_scheduler == 'cosine':
        is_cosine_scheduler = True
        scheduler = torch.optim.lr_scheduler.CosineAnnealingLR(
            optimizer,
            T_max=args.lr_max_iter,
            eta_min=1e-7,
            last_epoch=last_epoch)
    elif args.lr_scheduler == 'cosine_restarts':
        is_cosine_scheduler = True
        scheduler = torch.optim.lr_scheduler.CosineAnnealingWarmRestarts(
            optimizer, T_0=args.lr_max_iter, T_mult=2, last_epoch=last_epoch)

    elif args.lr_scheduler == 'exp':
        is_cosine_scheduler = False
        if last_epoch > 0:
            last_epoch /= max_batch_iters
        scheduler = torch.optim.lr_scheduler.ExponentialLR(
            optimizer, gamma=args.lr_decay, last_epoch=last_epoch)
    # elif args.lr_scheduler == 'step':
    # step_scheduler = torch.optim.lr_scheduler.StepLR(optimizer, 10, gamma=0.1)
    # scheduler = False
    else:
        is_cosine_scheduler = False
        scheduler = False

    for epoch in range(1, start_epoch):
        if args.lr_scheduler == 'cosine' and (epoch % epoch_to_change_lr == 0):
            scheduler.state_dict()['base_lrs'][0] *= args.lr_decay

    torch.autograd.set_detect_anomaly(True)
    for epoch in range(start_epoch, args.num_epochs + 1):
        print('Current epoch: ', epoch)

        # we don't need the average epoch loss so we assign it to _
        _ = train(epoch,
                  model,
                  loss,
                  optimizer,
                  dataloader,
                  pair_generation_tnf,
                  log_interval=args.log_interval,
                  scheduler=scheduler,
                  is_cosine_scheduler=is_cosine_scheduler,
                  tb_writer=logs_writer)

        # Step non-cosine scheduler
        if scheduler and not is_cosine_scheduler:
            scheduler.step()

        val_loss = validate_model(model, loss, dataloader_val,
                                  pair_generation_tnf, epoch, logs_writer)

        # Change lr_max in cosine annealing
        if args.lr_scheduler == 'cosine' and (epoch % epoch_to_change_lr == 0):
            scheduler.state_dict()['base_lrs'][0] *= args.lr_decay

        if (epoch % epoch_to_change_lr
                == epoch_to_change_lr // 2) or epoch == 1:
            compute_metric('absdiff', model, args.geometric_model, None, None,
                           dataset_val, dataloader_val, pair_generation_tnf,
                           args.batch_size, args)

        # remember best loss
        is_best = val_loss < best_val_loss
        best_val_loss = min(val_loss, best_val_loss)
        save_checkpoint(
            {
                'epoch': epoch + 1,
                'args': args,
                'state_dict': model.state_dict(),
                'best_val_loss': best_val_loss,
                'optimizer': optimizer.state_dict(),
            }, is_best, checkpoint_path)

    logs_writer.close()
    print('Done!')
Exemplo n.º 7
0
from image.normalization import NormalizeImageDict
from util.torch_util import save_checkpoint
from util.torch_util import BatchTensorToVars
from collections import OrderedDict
import numpy as np
import numpy.random
from scipy.ndimage.morphology import generate_binary_structure
from util.eval_util import compute_metric
from options.options import ArgumentParser
from geotnf.transformation import GeometricTnf
import config

print('WeakAlign training script using weak supervision')

# Argument parsing
args, arg_groups = ArgumentParser(mode='train_weak').parse()
print(args)

torch.cuda.set_device(args.gpu)
use_cuda = torch.cuda.is_available()

# Seed
torch.manual_seed(args.seed)
if use_cuda:
    torch.cuda.manual_seed(args.seed)
np.random.seed(args.seed)

# CNN model and loss
print('Creating CNN model...')

model = TwoStageCNNGeometric(use_cuda=use_cuda,
Exemplo n.º 8
0
from model.cnn_geometric_model import featureL2Norm
from util.dataloader import default_collate
from util.eval_util import pck_metric, area_metrics, flow_metrics, compute_metric
from options.options import ArgumentParser


"""

Script to train the model using weak supervision

"""

print('WeakAlign training script using weak supervision')

# Argument parsing
args,arg_groups = ArgumentParser(mode='train_weak').parse()
print(args)

use_cuda = torch.cuda.is_available()

# Seed
torch.manual_seed(args.seed)
if use_cuda:
    torch.cuda.manual_seed(args.seed)
np.random.seed(args.seed)

# CNN model and loss
print('Creating CNN model...')

model = TwoStageCNNGeometric(use_cuda=use_cuda,
                             return_correlation=True,
Exemplo n.º 9
0
import numpy as np
import numpy.random
from collections import OrderedDict
from options.options import ArgumentParser

"""

Script to train the model as presented in the CNNGeometric CVPR'17 paper
using synthetically warped image pairs and strong supervision

"""

print('CNNGeometric training script using strong supervision')

# Argument parsing
args,arg_groups = ArgumentParser(mode='train_strong').parse()
print(args)

# Seed and CUDA
use_cuda = torch.cuda.is_available()
torch.manual_seed(args.seed)
if use_cuda:
    torch.cuda.manual_seed(args.seed)
np.random.seed(args.seed)

# Download dataset if needed and set paths
if args.training_dataset == 'pascal':
    if args.dataset_image_path == '':
        if not exists('datasets/pascal-voc11/TrainVal'):
            download_pascal('datasets/pascal-voc11/')
        args.dataset_image_path = 'datasets/pascal-voc11/'        
Exemplo n.º 10
0
from scipy.ndimage.morphology import binary_dilation, generate_binary_structure
import torch.nn.functional as F
from model.cnn_geometric_model import featureL2Norm
from util.dataloader import default_collate
from util.eval_util import pck_metric, area_metrics, flow_metrics, compute_metric
from options.options import ArgumentParser
"""

Script to train the model using weak supervision

"""

print('WeakAlign training script using weak supervision')

# Argument parsing
args, arg_groups = ArgumentParser(mode='train_weak').parse()
print(args)

use_cuda = torch.cuda.is_available()

# Seed
torch.manual_seed(args.seed)
if use_cuda:
    torch.cuda.manual_seed(args.seed)
np.random.seed(args.seed)

# CNN model and loss
print('Creating CNN model...')

model = TwoStageCNNGeometric(use_cuda=use_cuda,
                             return_correlation=True,
Exemplo n.º 11
0
"""
this code is modified from 
https://github.com/utkuozbulak/pytorch-cnn-adversarial-attacks
https://github.com/louis2889184/pytorch-adversarial-training
https://github.com/MadryLab/robustness
https://github.com/yaodongyu/TRADES
"""

import torch
import torch.nn.functional as F
from model.loss import TransformedGridLoss
from options.options import ArgumentParser
from geotnf.transformation import SynthPairTnf

args, arg_groups = ArgumentParser(mode='train_strong').parse()

cnn_image_size = (args.image_size, args.image_size)

batch_preprocessing_fn = SynthPairTnf(geometric_model=args.geometric_model,
                                      output_size=cnn_image_size,
                                      use_cuda=True)


def project(x, original_x, epsilon, _type='linf'):

    if _type == 'linf':
        max_x = original_x + epsilon
        min_x = original_x - epsilon

        x = torch.max(torch.min(x, max_x), min_x)
    else:
def main():

    # Argument parsing
    args, arg_groups = ArgumentParser(mode='eval').parse()
    print(args)

    # check provided models and deduce if single/two-stage model should be used
    two_stage = args.model_2 != ''

    if args.eval_dataset_path == '' and args.eval_dataset == 'pf':
        args.eval_dataset_path = 'datasets/proposal-flow-willow/'

    if args.eval_dataset_path == '' and args.eval_dataset == 'pf-pascal':
        args.eval_dataset_path = 'datasets/proposal-flow-pascal/'

    if args.eval_dataset_path == '' and args.eval_dataset == 'caltech':
        args.eval_dataset_path = 'datasets/caltech-101/'

    if args.eval_dataset_path == '' and args.eval_dataset == 'tss':
        args.eval_dataset_path = 'datasets/tss/'

    use_cuda = torch.cuda.is_available()

    # Download dataset if needed
    if args.eval_dataset == 'pf' and not exists(args.eval_dataset_path):
        download_PF_willow(args.eval_dataset_path)

    elif args.eval_dataset == 'pf-pascal' and not exists(
            args.eval_dataset_path):
        download_PF_pascal(args.eval_dataset_path)

    elif args.eval_dataset == 'caltech' and not exists(args.eval_dataset_path):
        download_caltech(args.eval_dataset_path)

    elif args.eval_dataset == 'tss' and not exists(args.eval_dataset_path):
        download_TSS(args.eval_dataset_path)

    print('Creating CNN model...')

    def create_model(model_filename):
        checkpoint = torch.load(model_filename,
                                map_location=lambda storage, loc: storage)
        checkpoint['state_dict'] = OrderedDict([
            (k.replace('vgg', 'model'), v)
            for k, v in checkpoint['state_dict'].items()
        ])
        output_size = checkpoint['state_dict'][
            'FeatureRegression.linear.bias'].size()[0]

        if output_size == 6:
            geometric_model = 'affine'

        elif output_size == 8 or output_size == 9:
            geometric_model = 'hom'
        else:
            geometric_model = 'tps'

        model = CNNGeometric(use_cuda=use_cuda,
                             output_dim=output_size,
                             **arg_groups['model'])

        for name, param in model.FeatureExtraction.state_dict().items():
            if not name.endswith('num_batches_tracked'):
                model.FeatureExtraction.state_dict()[name].copy_(
                    checkpoint['state_dict']['FeatureExtraction.' + name])

        for name, param in model.FeatureRegression.state_dict().items():
            if not name.endswith('num_batches_tracked'):
                model.FeatureRegression.state_dict()[name].copy_(
                    checkpoint['state_dict']['FeatureRegression.' + name])

        return (model, geometric_model)

    # Load model for stage 1
    model_1, geometric_model_1 = create_model(args.model_1)

    if two_stage:
        # Load model for stage 2
        model_2, geometric_model_2 = create_model(args.model_2)
    else:
        model_2, geometric_model_2 = None, None

    #import pdb; pdb.set_trace()

    print('Creating dataset and dataloader...')

    # Dataset and dataloader
    if args.eval_dataset == 'pf':
        Dataset = PFDataset
        collate_fn = default_collate
        csv_file = 'test_pairs_pf.csv'

    if args.eval_dataset == 'pf-pascal':
        Dataset = PFPascalDataset
        collate_fn = default_collate
        csv_file = 'all_pairs_pf_pascal.csv'

    elif args.eval_dataset == 'caltech':
        Dataset = CaltechDataset
        collate_fn = default_collate
        csv_file = 'test_pairs_caltech_with_category.csv'

    elif args.eval_dataset == 'tss':
        Dataset = TSSDataset
        collate_fn = default_collate
        csv_file = 'test_pairs_tss.csv'

    cnn_image_size = (args.image_size, args.image_size)

    dataset = Dataset(csv_file=os.path.join(args.eval_dataset_path, csv_file),
                      dataset_path=args.eval_dataset_path,
                      transform=NormalizeImageDict(
                          ['source_image', 'target_image']),
                      output_size=cnn_image_size)

    if use_cuda:
        batch_size = args.batch_size

    else:
        batch_size = 1

    dataloader = DataLoader(dataset,
                            batch_size=batch_size,
                            shuffle=False,
                            num_workers=0,
                            collate_fn=collate_fn)

    batch_tnf = BatchTensorToVars(use_cuda=use_cuda)

    if args.eval_dataset == 'pf' or args.eval_dataset == 'pf-pascal':
        metric = 'pck'

    elif args.eval_dataset == 'caltech':
        metric = 'area'

    elif args.eval_dataset == 'tss':
        metric = 'flow'

    model_1.eval()

    if two_stage:
        model_2.eval()

    print('Starting evaluation...')

    stats = compute_metric(metric, model_1, geometric_model_1, model_2,
                           geometric_model_2, dataset, dataloader, batch_tnf,
                           batch_size, args)
Exemplo n.º 13
0
def main(passed_arguments=None):

    # Argument parsing
    args,arg_groups = ArgumentParser(mode='eval').parse(passed_arguments)
    print(args)

    # check provided models and deduce if single/two-stage model should be used
    two_stage = args.model_2 != ''
     
    use_cuda = torch.cuda.is_available()
    use_me = args.use_me

    print('Creating CNN model...')

    def create_model(model_filename):
        checkpoint = torch.load(model_filename, map_location=lambda storage, loc: storage)
        checkpoint['state_dict'] = OrderedDict([(k.replace('vgg', 'model'), v) for k, v in checkpoint['state_dict'].items()])
        try:
            output_size = checkpoint['state_dict']['FeatureRegression.linear.bias'].size()[0]
        except:
            output_size = checkpoint['state_dict']['FeatureRegression.resnet.fc.bias'].size()[0]
        if output_size == 4:
            geometric_model = 'affine_simple_4'
        elif output_size == 3:
            geometric_model = 'affine_simple'
        else:
            raise NotImplementedError('Geometric model deducted from output layer is unsupported')

        model = CNNGeometric(use_cuda=use_cuda,
                             output_dim=output_size,
                             **arg_groups['model'])

        if use_me is False:
            for name, param in model.FeatureExtraction.state_dict().items():
                if not name.endswith('num_batches_tracked'):
                    model.FeatureExtraction.state_dict()[name].copy_(checkpoint['state_dict']['FeatureExtraction.' + name])    

        for name, param in model.FeatureRegression.state_dict().items():
            if not name.endswith('num_batches_tracked'):
                model.FeatureRegression.state_dict()[name].copy_(checkpoint['state_dict']['FeatureRegression.' + name])

        return (model,geometric_model)

    # Load model for stage 1
    model_1, geometric_model_1 = create_model(args.model_1)

    if two_stage:
        # Load model for stage 2
        model_2, geometric_model_2 = create_model(args.model_2)
    else:
        model_2,geometric_model_2 = None, None

    #import pdb; pdb.set_trace()

    print('Creating dataset and dataloader...')

    # Dataset and dataloader
    if args.eval_dataset == '3d' and use_me is False:
        cnn_image_size=(args.image_size,args.image_size)
        dataset = Dataset3D(csv_file = os.path.join(args.eval_dataset_path, 'all_pairs.csv'),
                      dataset_path = args.eval_dataset_path,
                      transform = NormalizeImageDict(['source_image','target_image']),
                      output_size = cnn_image_size)
        collate_fn = default_collate
    elif args.eval_dataset == '3d' and use_me is True:
        cnn_image_size=(args.input_height, args.input_width)
        dataset = MEDataset(dataset_csv_path=args.eval_dataset_path, 
                            dataset_csv_file='all_pairs_3d.csv', 
                            dataset_image_path=args.eval_dataset_path,
                            input_height=args.input_height, input_width=args.input_width, 
                            crop=args.crop_factor, 
                            use_conf=args.use_conf, 
                            use_random_patch=args.use_random_patch,
                            normalize_inputs=args.normalize_inputs,
                            geometric_model='EVAL', 
                            random_sample=False)
        collate_fn = default_collate
    else:
        raise NotImplementedError('Dataset is unsupported')

    if use_cuda:
        batch_size = args.batch_size
    else:
        batch_size = 1

    dataloader = DataLoader(dataset, 
                            batch_size = batch_size,
                            shuffle = False,
                            num_workers=0,
                            collate_fn = collate_fn)

    batch_tnf = BatchTensorToVars(use_cuda = use_cuda)

    if args.eval_dataset == '3d':
        metric = 'absdiff'
    else:
        raise NotImplementedError('Dataset is unsupported')
        
    model_1.eval()

    if two_stage:
        model_2.eval()

    print(os.path.basename(args.model_1))
    print('Starting evaluation...', flush=True)
        
    stats=compute_metric(metric,
                         model_1,
                         geometric_model_1,
                         model_2,
                         geometric_model_2,
                         dataset,
                         dataloader,
                         batch_tnf,
                         batch_size,
                         args)
    if args.eval_dataset_path.find('merged') >= 0:
        stats_fn = 'stats_merged.pkl'
    else:
        stats_fn = 'stats.pkl'
    stats_fn = os.path.join(os.path.dirname(args.model_1), stats_fn)
    save_dict(stats_fn, stats)
    return stats