コード例 #1
0
def predict(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    if prep_config["test_10crop"]:
        prep_dict["database"] = prep.image_test_10crop( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
        prep_dict["test"] = prep.image_test_10crop( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    else:
        prep_dict["database"] = prep.image_test( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
        prep_dict["test"] = prep.image_test( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
               
    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["database"+str(i)] = ImageList(open(data_config["database"]["list_path"]).readlines(), \
                                transform=prep_dict["database"]["val"+str(i)])
            dset_loaders["database"+str(i)] = util_data.DataLoader(dsets["database"+str(i)], \
                                batch_size=data_config["database"]["batch_size"], \
                                shuffle=False, num_workers=4)
            dsets["test"+str(i)] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["test"+str(i)] = util_data.DataLoader(dsets["test"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

    else:
        dsets["database"] = ImageList(open(data_config["database"]["list_path"]).readlines(), \
                                transform=prep_dict["database"])
        dset_loaders["database"] = util_data.DataLoader(dsets["database"], \
                                batch_size=data_config["database"]["batch_size"], \
                                shuffle=False, num_workers=4)
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = util_data.DataLoader(dsets["test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)
    ## set base network
    base_network = torch.load(config["snapshot_path"])

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        base_network = base_network.cuda()

    database_codes, database_labels = code_predict(dset_loaders, base_network, "database", test_10crop=prep_config["test_10crop"], gpu=use_gpu)
    test_codes, test_labels = code_predict(dset_loaders, base_network, "test", test_10crop=prep_config["test_10crop"], gpu=use_gpu)

    return {"database_code":database_codes.numpy(), "database_labels":database_labels.numpy(), \
            "test_code":test_codes.numpy(), "test_labels":test_labels.numpy()}
コード例 #2
0
def run(config,path):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = 34
    test_bs = 34
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)
    dset_loaders["test1"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=False, num_workers=1, drop_last=False)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=0) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=0)

    n_class = config["network"]["params"]["class_num"]
    # for p in [499,999,1499,1999,2499,2999]:
    #     PATH = path + '/'+ str(p) + '_model.pth.tar'
    #
    #     model = load_model(PATH)
    #     base_network = model.cuda()
    #     fun1(dset_loaders, base_network, n_class)

    PATH = path+'/2999_model.pth.tar'

    model = load_model(PATH)
    base_network = model.cuda()
    # homo_cl = train_homo_cl(dset_loaders, base_network)

    fun1(dset_loaders, base_network, n_class, dsets)
コード例 #3
0
def run(config, model):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = 34
    test_bs = 34
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=False)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=False)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=0) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=0)

    n_class = config["network"]["params"]["class_num"]

    model.train(False)
    temp_acc = image_classification_test(dset_loaders, model, n_class=n_class)
    log_str = "precision: {:.5f}".format(temp_acc)
    print(log_str)
コード例 #4
0
def save(config, model, save_name):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = 34
    test_bs = 34
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=False)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=False)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=0) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=0)

    n_class = config["network"]["params"]["class_num"]

    model.train(False)
    save_feature(dset_loaders, model, './snapshot/model/', save_name)
コード例 #5
0
def train(config):
    # set pre-process
    prep_dict = {'source': prep.image_train(**config['prep']['params']),
                 'target': prep.image_train(**config['prep']['params'])}
    if config['prep']['test_10crop']:
        prep_dict['test'] = prep.image_test_10crop(**config['prep']['params'])
    else:
        prep_dict['test'] = prep.image_test(**config['prep']['params'])

    # prepare data
    data_set = {}
    data_set_loader = {}
    data_config = config['data']
    data_set['source'] = ImageList(open(data_config['source']['list_path']).readlines(),
                                   transform=prep_dict['source'])
    data_set_loader['source'] = torch.utils.data.DataLoader(data_set['source'],
                                                            batch_size=data_config['source']['batch_size'],
                                                            shuffle=True, num_workers=4, drop_last=True)
    data_set['target'] = ImageList(open(data_config['target']['list_path']).readlines(),
                                   transform=prep_dict['target'])
    data_set_loader['target'] = torch.utils.data.DataLoader(data_set['target'],
                                                            batch_size=data_config['target']['batch_size'],
                                                            shuffle=True, num_workers=4, drop_last=True)
    if config['prep']['test_10crop']:
        data_set['test'] = [ImageList(open(data_config['test']['list_path']).readlines(),
                                      transform=prep_dict['test'][i])
                            for i in range(10)]
        data_set_loader['test'] = [torch.utils.data.DataLoader(dset, batch_size=data_config['test']['batch_size'],
                                                               shuffle=False, num_workers=4)
                                   for dset in data_set['test']]
    else:
        data_set['test'] = ImageList(open(data_config['test']['list_path']).readlines(),
                                     transform=prep_dict['test'])
        data_set_loader['test'] = torch.utils.data.DataLoader(data_set['test'],
                                                              batch_size=data_config['test']['batch_size'],
                                                              shuffle=False, num_workers=4)

    # set base network
    net_config = config['network']
    base_net = net_config['name']()  # res50
    base_net = base_net.cuda()
    # add domain, classifier network
    class_num = config['network']['params']['class_num']
    ad_net = network.Domain(in_features=base_net.output_num(), hidden_size=1024)
    f1_net = network.Classifier(in_features=base_net.output_num(), hidden_size=128, class_num=class_num)
    f2_net = network.Classifier(in_features=base_net.output_num(), hidden_size=128, class_num=class_num)
    ad_net = ad_net.cuda()
    f1_net = f1_net.cuda()
    f2_net = f2_net.cuda()
    parameter_list = base_net.get_parameters() + ad_net.get_parameters() \
                     + f1_net.get_parameters() + f2_net.get_parameters()

    # multi gpus
    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        base_net = nn.DataParallel(base_net, device_ids=[int(i) for i in gpus])
        f1_net = nn.DataParallel(f1_net, device_ids=[int(i) for i in gpus])
        f2_net = nn.DataParallel(f2_net, device_ids=[int(i) for i in gpus])
        ad_net = nn.DataParallel(ad_net, device_ids=[int(i) for i in gpus])

    # set optimizer
    optimizer_config = config['optimizer']
    optimizer = optimizer_config['type'](parameter_list, **(optimizer_config['optim_params']))
    schedule_param = optimizer_config['lr_param']
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config['lr_type']]

    # set loss
    class_criterion = nn.CrossEntropyLoss()
    transfer_criterion = nn.BCELoss()
    loss_params = config['loss']

    # train
    len_train_source = len(data_set_loader['source'])
    len_train_taget = len(data_set_loader['target'])
    best_acc = 0.0
    since = time.time()
    for num_iter in tqdm(range(config['max_iter'])):
        if num_iter % config['val_iter'] == 0:
            base_net.train(False)
            f1_net.train(False)
            f2_net.train(False)
            temp_acc = val(data_set_loader, base_net, f1_net, f2_net,
                           test_10crop=config['prep']['test_10crop'],
                           config=config, num_iter=num_iter)
            if temp_acc > best_acc:
                best_acc = temp_acc
            log_str = 'iter: {:d}, accu: {:.4f}\ntime: {:.4f}'.format(num_iter, temp_acc, time.time() - since)
            config['logger'].logger.debug(log_str)
            config['results'][num_iter].append(temp_acc)
        if num_iter % config['snapshot_iter'] == 0:
            # TODO
            pass

        base_net.train(True)
        f1_net.train(True)
        f2_net.train(True)
        ad_net.train(True)

        optimizer = lr_scheduler(optimizer, num_iter, **schedule_param)
        optimizer.zero_grad()

        if num_iter % len_train_source == 0:
            iter_source = iter(data_set_loader['source'])
        if num_iter % len_train_taget == 0:
            iter_target = iter(data_set_loader['target'])
        input_source, label_source = iter_source.next()
        input_target, _ = iter_target.next()
        input_source, label_source, input_target = input_source.cuda(), label_source.cuda(), input_target.cuda()
        inputs = torch.cat((input_source, input_target), 0)
        batch_size = len(label_source)

        # class-wise adaptation
        features = base_net(inputs)
        alpha = 2. / (1. + np.exp(-10 * float(num_iter / config['max_iter']))) - 1
        output1 = f1_net(features, alpha)
        output2 = f2_net(features, alpha)
        output_s1 = output1[:batch_size, :]
        output_s2 = output2[:batch_size, :]
        output_t1 = output1[batch_size:, :]
        output_t2 = output2[batch_size:, :]
        output_t1 = F.softmax(output_t1)
        output_t2 = F.softmax(output_t2)

        inconsistency_loss = torch.mean(torch.abs(output_t1 - output_t2))
        classifier_loss1 = class_criterion(output_s1, label_source)
        classifier_loss2 = class_criterion(output_s2, label_source)
        classifier_loss = classifier_loss1 + classifier_loss2

        # domain-wise adaptation
        domain_labels = torch.from_numpy(np.array([[1]] * batch_size + [[0]] * batch_size)).float().cuda()
        domain_output = ad_net(features, alpha)
        transfer_loss = transfer_criterion(domain_output, domain_labels)

        total_loss = classifier_loss + loss_params['domain_off'] * transfer_loss \
                     - loss_params['dis_off'] * inconsistency_loss
        total_loss.backward()
        optimizer.step()

        if num_iter % config['val_iter'] == 0:
            print('class:', classifier_loss.item(),
                  'domain:', transfer_loss.item() * loss_params['domain_off'],
                  'inconsistency:', inconsistency_loss.item() * loss_params['dis_off'],
                  'total:', total_loss.item())
            if config['is_writer']:
                config['writer'].add_scalars('train', {'total': total_loss.item(), 'class': classifier_loss.item(),
                                                       'domain': transfer_loss.item() * loss_params['domain_off'],
                                                       'inconsistency': inconsistency_loss.item() * loss_params[
                                                           'dis_off']},
                                             num_iter)
    if config['is_writer']:
        config['writer'].close()

    return best_acc
コード例 #6
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=4, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=4, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                shuffle=False, num_workers=4) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.cuda()  #加载基础网络结构
    parameter_list = base_network.get_parameters()
    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                                         **(optimizer_config["optim_params"]))

    crit = LabelSmoothingLoss(smoothing=0.1, classes=31)  #标签平滑操作

    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        base_network = nn.DataParallel(base_network,
                                       device_ids=[int(i) for i in gpus])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    best_acc = 0.0
    start_time = time.time()
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == config["test_interval"] - 1:
            # 在这里进行测试的工作
            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders,
                                                 base_network,
                                                 test_10crop=False)
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()
            print(log_str)
            end_time = time.time()
            print('iter {} cost time {:.4f} sec.'.format(
                i, end_time - start_time))  # 打印时间间隔
            start_time = time.time()

        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                                                             "iter_{:05d}_model.pth.tar".format(i)))
        ## train one iter
        base_network.train(True)  # 训练模式
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()

        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])

        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(
        ), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)
        #目标域的熵正则化操作
        t_logit = outputs_target
        t_prob = F.softmax(t_logit)
        t_entropy_loss = get_entropy_loss(t_prob)  # 计算目标域的熵的损失
        entropy_loss = config['ENT_w'] * (t_entropy_loss)

        # classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)  # 源域的分类损失
        classifier_loss = crit(outputs_source, labels_source)

        total_loss = classifier_loss + entropy_loss
        if i % config["test_interval"] == config["test_interval"] - 1:
            print('total loss: {:.4f}, classifier loss: {:.4f}'.format(
                total_loss.item(), classifier_loss.item()))

        total_loss.backward()
        optimizer.step()
        if (i + 1) % 1000 == 0:
            model_path = os.path.join(
                os.path.dirname(config['save_model_name']), 'temp_model.pth')
            save_model(base_network, model_path)

    model_path = config['save_model_name']
    best_model_path = os.path.join(os.path.dirname(model_path),
                                   'best_model.pth')
    save_model(base_network, model_path)
    save_model(best_model, best_model_path)

    torch.save(best_model, osp.join(config["output_path"],
                                    "best_model.pth.tar"))
    return best_acc
コード例 #7
0
ファイル: train.py プロジェクト: jimchenhub/Xlearn
def transfer_classification(config):
    # ---set log writer ---
    writer = SummaryWriter(log_dir=config["log_dir"])
    # set pre-process
    prep_dict = {}
    for prep_config in config["prep"]:
        name = prep_config["name"]
        prep_dict[name] = {}
        if prep_config["type"] == "image":
            prep_dict[name]["test_10crop"] = prep_config["test_10crop"]
            prep_dict[name]["train"] = prep.image_train(resize_size=prep_config["resize_size"], crop_size=prep_config["crop_size"])
            if prep_config["test_10crop"]:
                prep_dict[name]["test"] = prep.image_test_10crop(resize_size=prep_config["resize_size"], crop_size=prep_config["crop_size"])
            else:
                prep_dict[name]["test"] = prep.image_test(resize_size=prep_config["resize_size"], crop_size=prep_config["crop_size"])
    # print(prep_dict)

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    loss_config = config["loss"]
    # transfer_criterion = loss.loss_dict[loss_config["name"]]
    if "params" not in loss_config:
        loss_config["params"] = {}
    # print(transfer_criterion)
    transfer_criterion = DANLoss(**loss_config["params"])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    for data_config in config["data"]:
        name = data_config['name']
        dsets[name] = {}
        dset_loaders[name] = {}
        ## image data
        if data_config["type"] == "image":
            dsets[name]["train"] = ImageList(open(data_config["list_path"]["train"]).readlines(), 
                                                            transform=prep_dict[name]["train"])
            dset_loaders[name]["train"] = util_data.DataLoader(dsets[name]["train"], 
                                                                batch_size=data_config["batch_size"]["train"], 
                                                                shuffle=True, num_workers=4)
            if "test" in data_config["list_path"]:
                if prep_dict[name]["test_10crop"]:
                    for i in range(10):
                        dsets[name]["test" + str(i)] = ImageList(
                            open(data_config["list_path"]["test"]).readlines(),
                            transform=prep_dict[name]["test"]["val" + str(i)])
                        dset_loaders[name]["test" + str(i)] = util_data.DataLoader(
                            dsets[name]["test" + str(i)], batch_size=data_config["batch_size"]["test"],
                            shuffle=False, num_workers=4)
                else:
                    dsets[name]["test"] = ImageList(
                        open(data_config["list_path"]["test"]).readlines(),
                        transform=prep_dict[name]["test"])
                    dset_loaders[name]["test"] = util_data.DataLoader(
                        dsets[name]["test"], batch_size = data_config["batch_size"]["test"],
                        shuffle=False, num_workers=4)
            else:
                if prep_dict[name]["test_10crop"]:
                    for i in range(10):
                        dsets[name]["test" + str(i)] = ImageList(
                            open(data_config["list_path"]["train"]).readlines(),
                            transform=prep_dict[name]["test"]["val" + str(i)])
                        dset_loaders[name]["test" + str(i)] = util_data.DataLoader(
                            dsets[name]["test" + str(i)], batch_size=data_config["batch_size"]["test"],
                            shuffle=False, num_workers=4)
                else:
                    dsets[name]["test"] = ImageList(open(data_config["list_path"]["train"]).readlines(),
                                                                   transform=prep_dict[name]["test"])
                    dset_loaders[data_config["name"]]["test"] = util_data.DataLoader(
                        dsets[data_config["name"]]["test"], batch_size=data_config["batch_size"]["test"],
                        shuffle=False, num_workers=4)

    class_num = 31

    ## set base network
    net_config = config["network"]
    base_network = network.network_dict[net_config["name"]]()
    if net_config["use_bottleneck"]:
        bottleneck_layer = nn.Linear(base_network.output_num(), net_config["bottleneck_dim"])
        classifier_layer = nn.Linear(bottleneck_layer.out_features, class_num)
    else:
        classifier_layer = nn.Linear(base_network.output_num(), class_num)

    ## initialization
    if net_config["use_bottleneck"]:
        bottleneck_layer.weight.data.normal_(0, 0.005)
        bottleneck_layer.bias.data.fill_(0.1)
        bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(), nn.Dropout(0.5))
    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)

    # print(base_network.state_dict())
    # print(classifier_layer.state_dict())

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        if net_config["use_bottleneck"]:
            bottleneck_layer = bottleneck_layer.to(device)
        classifier_layer = classifier_layer.to(device)
        base_network = base_network.to(device)


    ## collect parameters
    if net_config["use_bottleneck"]:
        parameter_list = [{"params":base_network.parameters(), "lr":1}, 
                          {"params":bottleneck_layer.parameters(), "lr":10}, 
                          {"params":classifier_layer.parameters(), "lr":10}]
       
    else:
        parameter_list = [{"params":base_network.parameters(), "lr":1}, 
                          {"params":classifier_layer.parameters(), "lr":10}]

    ## add additional network for some methods
    if loss_config["name"] == "JAN":
        softmax_layer = nn.Softmax()
        if use_gpu:
            softmax_layer = softmax_layer.to(device)
           
 
    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]


    ## train
    len_train_source = len(dset_loaders["source"]["train"]) - 1
    len_train_target = len(dset_loaders["target"]["train"]) - 1
    # transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    for i in range(config["num_iterations"]):
        # test in the train
        if i % config["test_interval"] == 0:
            base_network.train(False)
            classifier_layer.train(False)
            if net_config["use_bottleneck"]:
                bottleneck_layer.train(False)
                test_model = nn.Sequential(base_network, bottleneck_layer, classifier_layer)
                test_acc = image_classification_test(dset_loaders["target"],
                    test_model,
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)
                print("iteration: %d, test accuracy: %f" % (i, test_acc))

            else:
                test_model = nn.Sequential(base_network, classifier_layer)
                test_acc = image_classification_test(dset_loaders["target"],
                    test_model,
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)
                print("iteration: %d, test accuracy: %f" % (i, test_acc))
            # save model parameters
            if i % config["checkpoint_iterval"] == 0:
                torch.save(test_model.state_dict(), config["checkpoint_dir"]+"checkpoint_"+str(i).zfill(5)+".pth")

        # loss_test = nn.BCELoss()
        # train one iter
        base_network.train(True)
        if net_config["use_bottleneck"]:
            bottleneck_layer.train(True)
        classifier_layer.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"]["train"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"]["train"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        
        inputs_source = inputs_source.to(device)
        inputs_target = inputs_target.to(device)
        labels_source = labels_source.to(device)
          
        inputs = torch.cat((inputs_source, inputs_target), dim=0) ### cat the source and target 
        features = base_network(inputs)
        if net_config["use_bottleneck"]:
            features = bottleneck_layer(features)

        outputs = classifier_layer(features)

        # split the output for different loss
        num = inputs.size(0)//2
        # the premise is the batch size of source and target is the same
        classifier_loss = class_criterion(outputs.narrow(0, 0, num), labels_source)
        ## switch between different transfer loss
        if loss_config["name"] == "DAN":
            # transfer_loss = transfer_criterion(features.narrow(0, 0, num),
            #                                    features.narrow(0, num, num),
            #                                    **loss_config["params"])

            transfer_loss = transfer_criterion(features.narrow(0, 0, num),
                                               features.narrow(0, num, num))
        elif loss_config["name"] == "RTN":
            ## RTN is still under developing
            transfer_loss = 0
        elif loss_config["name"] == "JAN":
            softmax_out = softmax_layer(outputs)
            transfer_loss = transfer_criterion([features.narrow(0, 0, num), softmax_out.narrow(0, 0, num)],
                                               [features.narrow(0, num, num), softmax_out.narrow(0, num, num)],
                                               **loss_config["params"])

        total_loss = loss_config["trade_off"] * transfer_loss + classifier_loss
        if i % 100 == 0:
            print("iteration: ", str(i), "\t transfer loss: ", str(transfer_loss.item()),
                  "\t classification loss: ", str(classifier_loss.item()),
                  "\t total loss: ", str(total_loss.item()))
            for param_group in optimizer.param_groups:
                print("lr: ", param_group["lr"])
            # log for losses
            writer.add_scalar('Train/loss_classification', classifier_loss.item(), i//100)
            writer.add_scalar('Train/loss_transfer', transfer_loss.item(), i//100)
            writer.add_scalar('Train/loss_total', total_loss.item(), i//100)
        total_loss.backward()
        optimizer.step()
コード例 #8
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=0) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=0)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.cuda()

    ## add additional network for some methods
    if config["loss"]["random"]:
        random_layer = network.RandomLayer(
            [base_network.output_num(), class_num],
            config["loss"]["random_dim"])
        ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
    else:
        random_layer = None
        ad_net = network.AdversarialNetwork(
            base_network.output_num() * class_num, 1024)
    if config["loss"]["random"]:
        random_layer.cuda()
    ad_net = ad_net.cuda()
    parameter_list = base_network.get_parameters() + ad_net.get_parameters()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                                         **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        ad_net = nn.DataParallel(ad_net, device_ids=[int(i) for i in gpus])
        base_network = nn.DataParallel(base_network,
                                       device_ids=[int(i) for i in gpus])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    best_acc = 0.0
    best_model = nn.Sequential(base_network)
    each_log = ""
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == config["test_interval"] - 1:

            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders, \
                                                 base_network, test_10crop=prep_config["test_10crop"])
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}, transfer_loss:{:.4f}, classifier_loss:{:.4f}, total_loss:{:.4f}" \
                .format(i, temp_acc, transfer_loss.item(), classifier_loss.item(), total_loss.item())
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()
            print(log_str)

            config["out_file"].write(each_log)
            config["out_file"].flush()
            each_log = ""
        loss_params = config["loss"]
        ## train one iter
        base_network.train(True)
        ad_net.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(
        ), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)
        features = torch.cat((features_source, features_target), dim=0)
        outputs = torch.cat((outputs_source, outputs_target), dim=0)
        softmax_out = nn.Softmax(dim=1)(outputs)
        labels_target_fake = torch.max(nn.Softmax(dim=1)(outputs_target), 1)[1]
        labels = torch.cat((labels_source, labels_target_fake))
        entropy = loss.Entropy(softmax_out)
        transfer_loss = loss.CDAN([features, softmax_out], ad_net, entropy,
                                  network.calc_coeff(i), random_layer)

        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
        mdd_loss = loss.mdd_loss(features=features,
                                 labels=labels,
                                 left_weight=args.left_weight,
                                 right_weight=args.right_weight)
        max_entropy_loss = loss.EntropicConfusion(features)
        total_loss = loss_params["trade_off"] * transfer_loss \
                     + args.cls_weight * classifier_loss \
                     + args.mdd_weight * mdd_loss \
                     + args.entropic_weight * max_entropy_loss
        total_loss.backward()
        optimizer.step()
        log_str = "iter: {:05d},transfer_loss:{:.4f}, classifier_loss:{:.4f}, mdd_loss:{:4f}," \
                  "max_entropy_loss:{:.4f},total_loss:{:.4f}" \
            .format(i, transfer_loss.item(), classifier_loss.item(), mdd_loss.item(),
                    max_entropy_loss.item(), total_loss.item())
        each_log += log_str + "\n"

    torch.save(
        best_model, config['model_output_path'] + "{}_{}_p-{}_e-{}".format(
            config['log_name'], str(best_acc), str(config["mdd_weight"]),
            str(config["entropic_weight"])))
    return best_acc
コード例 #9
0
def train(config):
    ## set up summary writer
    writer = SummaryWriter(config['output_path'])

    # set up early stop
    early_stop_engine = EarlyStopping(config["early_stop_patience"])

    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    prep_dict["target"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    else:
        prep_dict["test"] = prep.image_test( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
               
    ## set loss
    class_num = config["network"]["params"]["class_num"]
    loss_params = config["loss"]

    class_criterion = nn.CrossEntropyLoss()
    transfer_criterion = loss.PADA
    center_criterion = loss_params["loss_type"](num_classes=class_num, 
                                       feat_dim=config["network"]["params"]["bottleneck_dim"])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    dsets["source"] = ImageList(stratify_sampling(open(data_config["source"]["list_path"]).readlines(), prep_config["source_size"]), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = util_data.DataLoader(dsets["source"], \
            batch_size=data_config["source"]["batch_size"], \
            shuffle=True, num_workers=1)
    dsets["target"] = ImageList(stratify_sampling(open(data_config["target"]["list_path"]).readlines(), prep_config["target_size"]), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = util_data.DataLoader(dsets["target"], \
            batch_size=data_config["target"]["batch_size"], \
            shuffle=True, num_workers=1)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"+str(i)] = ImageList(stratify_sampling(open(data_config["test"]["list_path"]).readlines(), ratio=prep_config['target_size']), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["test"+str(i)] = util_data.DataLoader(dsets["test"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=1)

            dsets["target"+str(i)] = ImageList(stratify_sampling(open(data_config["target"]["list_path"]).readlines(), ratio=prep_config['target_size']), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["target"+str(i)] = util_data.DataLoader(dsets["target"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=1)
    else:
        dsets["test"] = ImageList(stratify_sampling(open(data_config["test"]["list_path"]).readlines(), ratio=prep_config['target_size']), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = util_data.DataLoader(dsets["test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=1)

        dsets["target_test"] = ImageList(stratify_sampling(open(data_config["target"]["list_path"]).readlines(), ratio=prep_config['target_size']), \
                                transform=prep_dict["test"])
        dset_loaders["target_test"] = MyDataLoader(dsets["target_test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=1)

    config['out_file'].write("dataset sizes: source={}, target={}\n".format(
        len(dsets["source"]), len(dsets["target"])))

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])


    use_gpu = torch.cuda.is_available()
    if use_gpu:
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["params"]["new_cls"]:
        if net_config["params"]["use_bottleneck"]:
            parameter_list = [{"params":base_network.feature_layers.parameters(), "lr_mult":1, 'decay_mult':2}, \
                            {"params":base_network.bottleneck.parameters(), "lr_mult":10, 'decay_mult':2}, \
                            {"params":base_network.fc.parameters(), "lr_mult":10, 'decay_mult':2}]
        else:
            parameter_list = [{"params":base_network.feature_layers.parameters(), "lr_mult":1, 'decay_mult':2}, \
                            {"params":base_network.fc.parameters(), "lr_mult":10, 'decay_mult':2}]
    else:
        parameter_list = [{"params":base_network.parameters(), "lr_mult":1, 'decay_mult':2}]

    ## add additional network for some methods
    ad_net = network.AdversarialNetwork(base_network.output_num())
    gradient_reverse_layer = network.AdversarialLayer(high_value=config["high"]) #, 
                                                      #max_iter_value=config["num_iterations"])
    if use_gpu:
        ad_net = ad_net.cuda()
    parameter_list.append({"params":ad_net.parameters(), "lr_mult":10, 'decay_mult':2})
    parameter_list.append({"params":center_criterion.parameters(), "lr_mult": 10, 'decay_mult':1})
 
    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]


    ## train   
    len_train_source = len(dset_loaders["source"]) - 1
    len_train_target = len(dset_loaders["target"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == 0:
            base_network.train(False)
            if config['loss']['ly_type'] == "cosine":
                temp_acc = image_classification_test(dset_loaders, \
                    base_network, test_10crop=prep_config["test_10crop"], \
                    gpu=use_gpu)
            elif config['loss']['ly_type'] == "euclidean":
                temp_acc, _ = distance_classification_test(dset_loaders, \
                    base_network, center_criterion.centers.detach(), test_10crop=prep_config["test_10crop"], \
                    gpu=use_gpu)
            else:
                raise ValueError("no test method for cls loss: {}".format(config['loss']['ly_type']))
            
            snapshot_obj = {'step': i, 
                            "base_network": base_network.state_dict(), 
                            'precision': temp_acc, 
                            }
            if config["loss"]["loss_name"] != "laplacian" and config["loss"]["ly_type"] == "euclidean":
                snapshot_obj['center_criterion'] = center_criterion.state_dict()
            if temp_acc > best_acc:
                best_acc = temp_acc
                # save best model
                torch.save(snapshot_obj, 
                           osp.join(config["output_path"], "best_model.pth.tar"))
            log_str = "iter: {:05d}, {} precision: {:.5f}\n".format(i, config['loss']['ly_type'], temp_acc)
            config["out_file"].write(log_str)
            config["out_file"].flush()
            writer.add_scalar("precision", temp_acc, i)

            if early_stop_engine.is_stop_training(temp_acc):
                config["out_file"].write("no improvement after {}, stop training at step {}\n".format(
                    config["early_stop_patience"], i))
                # config["out_file"].write("finish training! \n")
                break

        if (i+1) % config["snapshot_interval"] == 0:
            torch.save(snapshot_obj, 
                       osp.join(config["output_path"], "iter_{:05d}_model.pth.tar".format(i)))
        

        ## train one iter
        base_network.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = \
                Variable(inputs_source).cuda(), Variable(inputs_target).cuda(), \
                Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(inputs_source), \
                Variable(inputs_target), Variable(labels_source)
           
        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        source_batch_size = inputs_source.size(0)

        if config['loss']['ly_type'] == 'cosine':
            features, logits = base_network(inputs)
            source_logits = logits.narrow(0, 0, source_batch_size)
        elif config['loss']['ly_type'] == 'euclidean':
            features, _ = base_network(inputs)
            logits = -1.0 * loss.distance_to_centroids(features, center_criterion.centers.detach())
            source_logits = logits.narrow(0, 0, source_batch_size)

        ad_net.train(True)
        weight_ad = torch.ones(inputs.size(0))
        transfer_loss = transfer_criterion(features, ad_net, gradient_reverse_layer, \
                                           weight_ad, use_gpu)
        ad_out, _ = ad_net(features.detach())
        ad_acc, source_acc_ad, target_acc_ad = domain_cls_accuracy(ad_out)

        # source domain classification task loss
        classifier_loss = class_criterion(source_logits, labels_source)
        # fisher loss on labeled source domain
        fisher_loss, fisher_intra_loss, fisher_inter_loss, center_grad = center_criterion(features.narrow(0, 0, int(inputs.size(0)/2)), labels_source, inter_class=config["loss"]["inter_type"], 
                                                                               intra_loss_weight=loss_params["intra_loss_coef"], inter_loss_weight=loss_params["inter_loss_coef"])
        # entropy minimization loss
        em_loss = loss.EntropyLoss(nn.Softmax(dim=1)(logits))

        # final loss
        total_loss = loss_params["trade_off"] * transfer_loss \
                     + fisher_loss \
                     + loss_params["em_loss_coef"] * em_loss \
                     + classifier_loss

        total_loss.backward()
        if center_grad is not None:
            # clear mmc_loss
            center_criterion.centers.grad.zero_()
            # Manually assign centers gradients other than using autograd
            center_criterion.centers.backward(center_grad)

        optimizer.step()

        if i % config["log_iter"] == 0:
            config['out_file'].write('iter {}: total loss={:0.4f}, transfer loss={:0.4f}, cls loss={:0.4f}, '
                'em loss={:0.4f}, '
                'mmc loss={:0.4f}, intra loss={:0.4f}, inter loss={:0.4f}, '
                'ad acc={:0.4f}, source_acc={:0.4f}, target_acc={:0.4f}\n'.format(
                i, total_loss.data.cpu().float().item(), transfer_loss.data.cpu().float().item(), classifier_loss.data.cpu().float().item(), 
                em_loss.data.cpu().float().item(), 
                fisher_loss.cpu().float().item(), fisher_intra_loss.cpu().float().item(), fisher_inter_loss.cpu().float().item(),
                ad_acc, source_acc_ad, target_acc_ad, 
                ))

            config['out_file'].flush()
            writer.add_scalar("total_loss", total_loss.data.cpu().float().item(), i)
            writer.add_scalar("cls_loss", classifier_loss.data.cpu().float().item(), i)
            writer.add_scalar("transfer_loss", transfer_loss.data.cpu().float().item(), i)
            writer.add_scalar("ad_acc", ad_acc, i)
            writer.add_scalar("d_loss/total", fisher_loss.data.cpu().float().item(), i)
            writer.add_scalar("d_loss/intra", fisher_intra_loss.data.cpu().float().item(), i)
            writer.add_scalar("d_loss/inter", fisher_inter_loss.data.cpu().float().item(), i)
        
    return best_acc
コード例 #10
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=0) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=0)

    # class_num = config["network"]["params"]["class_num"]
    n_class = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network_stu = net_config["name"](**net_config["params"]).cuda()
    base_network_tea = net_config["name"](**net_config["params"]).cuda()

    ## add additional network for some methods
    if config["loss"]["random"]:
        random_layer = network.RandomLayer([base_network_stu.output_num(), n_class], config["loss"]["random_dim"])
        ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
    else:
        random_layer = None

        if config['method'] == 'DANN':
            ad_net = network.AdversarialNetwork(base_network_stu.output_num(), 1024)#DANN
        else:
            ad_net = network.AdversarialNetwork(base_network_stu.output_num() * n_class, 1024)

    if config["loss"]["random"]:
        random_layer.cuda()
    ad_net = ad_net.cuda()
    ad_net2 = network.AdversarialNetwork(n_class, n_class*4)
    ad_net2.cuda()

    parameter_list = base_network_stu.get_parameters() + ad_net.get_parameters()

    teacher_params = list(base_network_tea.parameters())
    for param in teacher_params:
        param.requires_grad = False

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                                         **(optimizer_config["optim_params"]))

    teacher_optimizer = EMAWeightOptimizer(base_network_tea, base_network_stu, alpha=0.99)

    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    best_acc = 0.0

    output1(log_name)

    loss1, loss2, loss3, loss4, loss5,loss6 = 0, 0, 0, 0, 0,0

    output1('    =======    DA TRAINING    =======    ')

    best1 = 0
    f_t_result = []
    max_iter = config["num_iterations"]
    for i in range(max_iter+1):
        if i % config["test_interval"] == config["test_interval"] - 1 and i > 1500:
            base_network_tea.train(False)
            base_network_stu.train(False)

            # print("test")
            if 'MT' in config['method']:
                temp_acc = image_classification_test(dset_loaders,
                                                     base_network_tea, test_10crop=prep_config["test_10crop"])
                if temp_acc > best_acc:
                    best_acc = temp_acc

                log_str = "iter: {:05d}, tea_precision: {:.5f}".format(i, temp_acc)
                output1(log_str)
                #
                # if i > 20001 and best_acc < 0.69:
                #     break
                #
                # if temp_acc < 0.67:
                #     break
                #
                # if i > 30001 and best_acc < 0.71:
                #     break
                    # torch.save(base_network_tea, osp.join(path, "_model.pth.tar"))

                # temp_acc = image_classification_test(dset_loaders,
                #                                      base_network_stu, test_10crop=prep_config["test_10crop"])
                if temp_acc > best_acc:
                    best_acc = temp_acc
                    torch.save(base_network_stu, osp.join(path, "_model.pth.tar"))
                # log_str = "iter: {:05d}, stu_precision: {:.5f}".format(i, temp_acc)
                # output1(log_str)
            else:
                temp_acc = image_classification_test(dset_loaders,
                                                     base_network_stu, test_10crop=prep_config["test_10crop"])
                if temp_acc > best_acc:
                    best_acc = temp_acc
                    torch.save(base_network_stu, osp.join(path,"_model.pth.tar"))
                log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
                output1(log_str)

        loss_params = config["loss"]
        ## train one iter
        base_network_stu.train(True)
        base_network_tea.train(True)

        ad_net.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()

        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])

        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()

        inputs_source, inputs_target, labels_source = inputs_source.cuda(), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network_stu(inputs_source)

        features_target_stu, outputs_target_stu = base_network_stu(inputs_target)
        features_target_tea, outputs_target_tea = base_network_tea(inputs_target)

        softmax_out_source = nn.Softmax(dim=1)(outputs_source)
        softmax_out_target_stu = nn.Softmax(dim=1)(outputs_target_stu)
        softmax_out_target_tea = nn.Softmax(dim=1)(outputs_target_tea)

        features = torch.cat((features_source, features_target_stu), dim=0)

        if 'MT' in config['method']:
            softmax_out = torch.cat((softmax_out_source, softmax_out_target_tea), dim=0)

        else:
            softmax_out = torch.cat((softmax_out_source, softmax_out_target_stu), dim=0)

        vat_loss = VAT(base_network_stu).cuda()

        n, d = features_source.shape
        decay = cal_decay(start=1,end=0.6,i = i)
        # image number in each class
        s_labels = labels_source
        t_max, t_labels = torch.max(softmax_out_target_tea, 1)
        t_max, t_labels = t_max.cuda(), t_labels.cuda()
        if config['method'] == 'DANN+dis' or config['method'] == 'CDRL':
            pass

        elif config['method'] == 'RESNET':
            classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            total_loss = classifier_loss

        elif config['method'] == 'CDAN+E':
            entropy = losssntg.Entropy(softmax_out)
            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, entropy, network.calc_coeff(i),
                                          random_layer)

            transfer_loss = loss_params["trade_off"] * ad_loss
            classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            total_loss = transfer_loss + classifier_loss


        elif config['method'] == 'CDAN':
            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, None, None, random_layer)

            transfer_loss = loss_params["trade_off"] * ad_loss
            classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            total_loss = transfer_loss + classifier_loss


        elif config['method'] == 'DANN':

            ad_loss = losssntg.DANN(features, ad_net)
            transfer_loss = loss_params["trade_off"] * ad_loss
            classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            total_loss = transfer_loss + classifier_loss


        elif config['method'] == 'CDAN+MT':
            th = config['th']

            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, None, None, random_layer)
            unsup_loss = compute_aug_loss(softmax_out_target_stu, softmax_out_target_tea, n_class,confidence_thresh=th)
            unsup_loss = compute_aug_loss2(softmax_out_target_stu, softmax_out_target_tea, n_class,confidence_thresh=th)

            transfer_loss = loss_params["trade_off"] * ad_loss \
                            + 0.01 * unsup_loss
            classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            total_loss = transfer_loss + classifier_loss

        elif config['method'] == 'CDAN+MT+VAT':
            cent = ConditionalEntropyLoss().cuda()
            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, None, None, random_layer)
            unsup_loss = compute_aug_loss(softmax_out_target_stu, softmax_out_target_tea, n_class)
            loss_trg_cent = 1e-2 * cent(outputs_target_stu)
            loss_trg_vat = 1e-2 * vat_loss(inputs_target, outputs_target_stu)
            transfer_loss = loss_params["trade_off"] * ad_loss \
                            + 0.001*(unsup_loss + loss_trg_cent + loss_trg_vat)
            classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            total_loss = transfer_loss + classifier_loss

        elif config['method'] == 'CDAN+MT+cent+VAT+temp':
            th = 0.7
            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, None, None, random_layer)
            unsup_loss = compute_aug_loss(softmax_out_target_stu, softmax_out_target_tea, n_class,confidence_thresh=th)
            cent = ConditionalEntropyLoss().cuda()
            # loss_src_vat = vat_loss(inputs_source, outputs_source)
            loss_trg_cent = 1e-2 * cent(outputs_target_stu)
            loss_trg_vat = 1e-2 * vat_loss(inputs_target, outputs_target_stu)
            transfer_loss = loss_params["trade_off"] * ad_loss \
                            + unsup_loss + loss_trg_cent + loss_trg_vat
            # temperature
            classifier_loss = nn.NLLLoss()(nn.LogSoftmax(1)(outputs_source / 1.05), labels_source)
            total_loss = transfer_loss + classifier_loss

        elif config['method'] == 'CDAN+MT+cent+VAT+weightCross+T':

            if i % len_train_target == 0:

                if i != 0:
                    # print(cnt)
                    cnt = torch.tensor(cnt).float()
                    weight = cnt.sum() - cnt
                    weight = weight.cuda()
                else:
                    weight = torch.ones(n_class).cuda()

                cnt = [0] * n_class


            for j in t_labels:
                cnt[j.item()] += 1


            a = config['a']
            b = config['b']
            th = config['th']
            temp = config['temp']

            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, None, None, random_layer)
            unsup_loss = compute_aug_loss2(softmax_out_target_stu, softmax_out_target_tea, n_class,confidence_thresh=th)
            # cbloss = compute_cbloss(softmax_out_target_stu, n_class, cls_balance=0.05)
            # unsup_loss = compute_aug_loss(softmax_out_target_stu, softmax_out_target_tea, n_class,confidence_thresh=th)

            cent = ConditionalEntropyLoss().cuda()

            # loss_src_vat = vat_loss(inputs_source, outputs_source)
            loss_trg_cent = 1e-2 * cent(outputs_target_stu)
            loss_trg_vat = 1e-2 * vat_loss(inputs_target, outputs_target_stu)
            classifier_loss = nn.CrossEntropyLoss(weight=weight)(outputs_source/temp, labels_source)
            # classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            transfer_loss = loss_params["trade_off"] * ad_loss \
                + a*unsup_loss + b*(loss_trg_vat+loss_trg_cent)

            total_loss = transfer_loss + classifier_loss

        elif config['method'] == 'CDAN+MT+E+VAT+weightCross+T':
            entropy = losssntg.Entropy(softmax_out)
            if i % len_train_target == 0:

                if i != 0:
                    # print(cnt)
                    cnt = torch.tensor(cnt).float()
                    weight = cnt.sum() - cnt
                    weight = weight.cuda()
                else:
                    weight = torch.ones(n_class).cuda()

                cnt = [0] * n_class

            for j in t_labels:
                cnt[j.item()] += 1

            a = config['a']
            b = config['b']
            th = config['th']
            temp = config['temp']

            ad_loss = losssntg.CDANori([features, softmax_out], ad_net, entropy, network.calc_coeff(i),
                                       random_layer)            # unsup_loss = compute_aug_loss2(softmax_out_target_stu, softmax_out_target_tea, n_class,confidence_thresh=th)
            # cbloss = compute_cbloss(softmax_out_target_stu, n_class, cls_balance=0.05)
            unsup_loss = compute_aug_loss(softmax_out_target_stu, softmax_out_target_tea, n_class, confidence_thresh=th)

            cent = ConditionalEntropyLoss().cuda()

            # loss_src_vat = vat_loss(inputs_source, outputs_source)
            loss_trg_cent = 1e-2 * cent(outputs_target_stu)
            loss_trg_vat = 1e-2 * vat_loss(inputs_target, outputs_target_stu)
            classifier_loss = nn.CrossEntropyLoss(weight=weight)(outputs_source / temp, labels_source)
            # classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
            transfer_loss = loss_params["trade_off"] * ad_loss \
                            + a * unsup_loss + b * (loss_trg_vat + loss_trg_cent)

            total_loss = transfer_loss + classifier_loss

        # adout
        # ad_out1 = ad_net(features_source)
        # w = 1-ad_out1
        # c = w * nn.CrossEntropyLoss(reduction='none')(outputs_source, labels_source)
        # classifier_loss = c.mean()
        # total_loss = transfer_loss + classifier_loss
        total_loss.backward()
        optimizer.step()
        teacher_optimizer.step()

        loss1 += ad_loss.item()
        loss2 += classifier_loss.item()
        # loss3 += unsup_loss.item()
        # loss4 += loss_trg_cent.item()
        # loss5 += loss_trg_vat.item()
        # loss6 += cbloss.item()
        # dis_sloss_l += sloss_l.item()

        if i % 50 == 0 and i != 0:
            output1('iter:{:d}, ad_loss_D:{:.2f}, closs:{:.2f}, unsup_loss:{:.2f}, loss_trg_cent:{:.2f}, loss_trg_vatcd:{:.2f}, cbloss:{:.2f}'
                    .format(i, loss1, loss2, loss3, loss4, loss5,loss6))
            loss1, loss2, loss3, loss4, loss5, loss6 = 0, 0, 0, 0, 0, 0

    # torch.save(best_model, osp.join(path, "best_model.pth.tar"))
    return best_acc
コード例 #11
0
    dataset_loaders["val"] = torch.utils.data.DataLoader(
        dataset_list,
        batch_size=args.batch_size,
        shuffle=True,
        num_workers=args.num_workers)

    dataset_list = ImageList(open(dataset_test).readlines(),
                             transform=prep.image_train(resize_size=256,
                                                        crop_size=224))
    dataset_loaders["test"] = torch.utils.data.DataLoader(
        dataset_list,
        batch_size=4,
        shuffle=False,
        num_workers=args.num_workers)

    prep_dict_test = prep.image_test_10crop(resize_size=256, crop_size=224)
    for i in range(10):
        dataset_list = ImageList(open(dataset_test).readlines(),
                                 transform=prep_dict_test["val" + str(i)])
        dataset_loaders["val" + str(i)] = torch.utils.data.DataLoader(
            dataset_list, batch_size=4, shuffle=False, num_workers=6)

    # network construction
    feature_len = 2048
    # fine-grained feature extractor + fine-grained label predictor
    devices = list(range(torch.cuda.device_count()))
    model_fc = model_no.Resnet50Fc()
    model_fc = model_fc.to(device)
    model_fc = nn.DataParallel(model_fc, device_ids=devices)
    my_fine_net = fine_net(feature_len)
    my_fine_net = my_fine_net.to(device)
コード例 #12
0
ファイル: train.py プロジェクト: minqukanq/AI4SE
def transfer_classification(config):
    ## set pre-process
    prep_dict = {}
    for prep_config in config["prep"]:
        prep_dict[prep_config["name"]] = {}
        if prep_config["type"] == "image":
            prep_dict[prep_config["name"]]["test_10crop"] = prep_config[
                "test_10crop"]
            prep_dict[prep_config["name"]]["train"] = prep.image_train(
                resize_size=prep_config["resize_size"],
                crop_size=prep_config["crop_size"])
            if prep_config["test_10crop"]:
                prep_dict[
                    prep_config["name"]]["test"] = prep.image_test_10crop(
                        resize_size=prep_config["resize_size"],
                        crop_size=prep_config["crop_size"])
            else:
                prep_dict[prep_config["name"]]["test"] = prep.image_test(
                    resize_size=prep_config["resize_size"],
                    crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()

    loss_config = config["loss"]
    transfer_criterion = loss.loss_dict[loss_config["name"]]
    if "params" not in loss_config:
        loss_config["params"] = {}

    ## prepare data
    dsets = {}
    dset_loaders = {}
    for data_config in config["data"]:
        dsets[data_config["name"]] = {}
        dset_loaders[data_config["name"]] = {}
        ## image data
        if data_config["type"] == "image":
            dsets[data_config["name"]]["train"] = ImageList(
                open(data_config["list_path"]["train"]).readlines(),
                transform=prep_dict[data_config["name"]]["train"])
            dset_loaders[data_config["name"]]["train"] = util_data.DataLoader(
                dsets[data_config["name"]]["train"],
                batch_size=data_config["batch_size"]["train"],
                shuffle=True,
                num_workers=4)

            if "test" in data_config["list_path"]:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["test"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["test"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)
            else:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["train"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["train"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)

    class_num = 2

    ## set base network
    net_config = config["network"]
    base_network = network.network_dict[net_config["name"]]()
    if net_config["use_bottleneck"]:
        bottleneck_layer = nn.Linear(base_network.output_num(),
                                     net_config["bottleneck_dim"])
        classifier_layer = nn.Linear(bottleneck_layer.out_features, class_num)
    else:
        classifier_layer = nn.Linear(base_network.output_num(), class_num)
    for param in base_network.parameters():
        param.requires_grad = True

    ## initialization
    if net_config["use_bottleneck"]:
        bottleneck_layer.weight.data.normal_(0, 0.005)
        bottleneck_layer.bias.data.fill_(0.1)
        bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(),
                                         nn.Dropout(0.5))
    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        if net_config["use_bottleneck"]:
            bottleneck_layer = bottleneck_layer.cuda()
        classifier_layer = classifier_layer.cuda()
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["use_bottleneck"]:
        parameter_list = [{
            "params": base_network.parameters(),
            "lr": 10
        }, {
            "params": bottleneck_layer.parameters(),
            "lr": 10
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    else:
        parameter_list = [{
            "params": base_network.parameters(),
            "lr": 10
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](
        parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]["train"]) - 1
    len_train_target = len(dset_loaders["target"]["train"]) - 1
    F_best = 0
    mmd_meter = AverageMeter()
    for i in range(config["num_iterations"]):
        ## test in the train
        if i % config["test_interval"] == 0:
            base_network.train(False)
            classifier_layer.train(False)
            if net_config["use_bottleneck"]:
                bottleneck_layer.train(False)
                test_acc, F = image_classification_test(
                    dset_loaders["target"],
                    nn.Sequential(base_network, bottleneck_layer,
                                  classifier_layer),
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)

            else:
                test_acc, F = image_classification_test(
                    dset_loaders["target"],
                    nn.Sequential(base_network, classifier_layer),
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)

            print(args.source + '->' + args.target)
            print('Iter: %d, mmd = %.4f, test_acc = %.3f, f1 score = %.4f' %
                  (i, mmd_meter.avg, test_acc, F))
            mmd_meter.reset()

            if F_best < F:
                F_best = F

        ## train one iter
        if net_config["use_bottleneck"]:
            bottleneck_layer.train(True)
        classifier_layer.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        # optimzer4center = optim.SGD(lmcl_loss.parameters(), lr=0.05)
        # sheduler_4center = lr_scheduler_torch.StepLR(optimizer, 20, gamma=0.5)

        # optimizer.zero_grad()
        # optimzer4center.zero_grad()

        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"]["train"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"]["train"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()

        if use_gpu:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source).cuda(), Variable(
                    inputs_target).cuda(), Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source), Variable(inputs_target), Variable(
                    labels_source)

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features = base_network(inputs)
        if net_config["use_bottleneck"]:
            features = bottleneck_layer(features)

        outputs = classifier_layer(features)

        #
        # logits, mlogits = lmcl_loss(outputs.narrow(0, 0, int(inputs.size(0)/2)), labels_source)
        # classifier_loss = class_criterion(mlogits, labels_source)

        classifier_loss = class_criterion(
            outputs.narrow(0, 0, int(inputs.size(0) / 2)), labels_source)

        ## switch between different transfer loss
        if loss_config["name"] == "DAN" or loss_config["name"] == "DAN_Linear":
            transfer_loss = transfer_criterion(
                features.narrow(0, 0, int(features.size(0) / 2)),
                features.narrow(0, int(features.size(0) / 2),
                                int(features.size(0) / 2)),
                **loss_config["params"])

        mmd_meter.update(transfer_loss.item(), inputs_source.size(0))
        # mmd_meter.update(transfer_loss.data[0], inputs_source.size(0))
        total_loss = loss_config["trade_off"] * transfer_loss + classifier_loss
        # total_loss = classifier_loss
        total_loss.backward()
        optimizer.step()

        # optimzer4center.step()
        # sheduler_4center.step()

    print(args.source + '->' + args.target)
    print(F_best)
コード例 #13
0
ファイル: office31_center.py プロジェクト: chenwdyy/C2FAN
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=4, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=4, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=4) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]
    crit = LabelSmoothingLoss(smoothing=0.05, classes=class_num)#标签平滑操作

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.cuda()  # 加载基础网络结构

    ## add additional network for some methods
    if config["loss"]["random"]:
        random_layer = network.RandomLayer([base_network.output_num(), class_num], config["loss"]["random_dim"])
        ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
    else:
        random_layer = None
        ad_net = network.AdversarialNetwork(base_network.output_num() * class_num, 1024)  # 对抗网络结构
    if config["loss"]["random"]:
        random_layer.cuda()
    ad_net = ad_net.cuda()
    parameter_list = base_network.get_parameters() + ad_net.get_parameters()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                                         **(optimizer_config["optim_params"]))

    #中心损失函数
    criterion_centor=CenterLoss(num_classes=class_num,feat_dim=256,use_gpu=True)
    optimizer_centerloss=torch.optim.SGD(criterion_centor.parameters(),lr=config['lr'])

    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        ad_net = nn.DataParallel(ad_net, device_ids=[int(i) for i in gpus])
        base_network = nn.DataParallel(base_network, device_ids=[int(i) for i in gpus])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    start_time = time.time()
    for i in range(config["num_iterations"]):

        if i % config["test_interval"] == config["test_interval"] - 1:
            # 在这里进行测试的工作
            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders, \
                                                 base_network, test_10crop=prep_config["test_10crop"])
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()
            print(log_str)
            end_time = time.time()
            print('iter {} cost time {:.4f} sec.'.format(i, end_time - start_time))  # 打印时间间隔
            start_time = time.time()

        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                                                             "iter_{:05d}_model.pth.tar".format(i)))

        loss_params = config["loss"]

        ## train one iter
        base_network.train(True)  # 训练模式
        ad_net.train(True)

        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        # optimizer_centerloss=lr_scheduler(optimizer_centerloss, i, **schedule_param)

        optimizer.zero_grad()
        optimizer_centerloss.zero_grad()

        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)
        features = torch.cat((features_source, features_target), dim=0)
        outputs = torch.cat((outputs_source, outputs_target), dim=0)
        softmax_out = nn.Softmax(dim=1)(outputs)
        if config['method'] == 'CDAN+E':
            entropy = loss.Entropy(softmax_out)
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, entropy, network.calc_coeff(i), random_layer)
        elif config['method'] == 'CDAN':
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, None, None, random_layer)
        elif config['method'] == 'DANN':
            transfer_loss = loss.DANN(features, ad_net)
        else:
            raise ValueError('Method cannot be recognized.')
        # classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)  # 源域的分类损失
        classifier_loss = crit(outputs_source, labels_source)  # 源域的分类损失,标签平滑操作

        # 目标域的熵正则化操作
        outputs_target=outputs[len(inputs_source):,:]
        t_logit = outputs_target
        t_prob = torch.softmax(t_logit,dim=1)
        t_entropy_loss = get_entropy_loss(t_prob)  # 计算目标域的熵的损失
        entropy_loss = 0.05 * (t_entropy_loss)

        # 计算中心损失函数
        loss_centor = criterion_centor(features_source, labels_source)  # 中心损失计算

        total_loss = loss_params["trade_off"] * transfer_loss + classifier_loss + config['centor_w']*loss_centor
        if i % config["test_interval"] == config["test_interval"] - 1:
            print('total loss: {:.4f}, transfer loss: {:.4f}, classifier loss: {:.4f}, centor loss: {:.4f}'.format(
                total_loss.item(),transfer_loss.item(),classifier_loss.item(),config['centor_w']*loss_centor.item()
            ))
        total_loss.backward()
        optimizer.step()
        # by doing so, weight_cent would not impact on the learning of centers
        for param in criterion_centor.parameters():
            param.grad.data *= (1. / config['centor_w'])
        optimizer_centerloss.step()

    torch.save(best_model, osp.join(config["output_path"], "best_model.pth.tar"))
    return best_acc
コード例 #14
0
def transfer_classification(config):
    # ---set log writer ---
    writer = SummaryWriter(log_dir=config["log_dir"])
    # set pre-process
    prep_dict = {}
    for prep_config in config["prep"]:
        name = prep_config["name"]
        prep_dict[name] = {}
        if prep_config["type"] == "image":
            prep_dict[name]["test_10crop"] = prep_config["test_10crop"]
            prep_dict[name]["train"] = prep.image_train(
                resize_size=prep_config["resize_size"],
                crop_size=prep_config["crop_size"])
            if prep_config["test_10crop"]:
                prep_dict[name]["test"] = prep.image_test_10crop(
                    resize_size=prep_config["resize_size"],
                    crop_size=prep_config["crop_size"])
            else:
                prep_dict[name]["test"] = prep.image_test(
                    resize_size=prep_config["resize_size"],
                    crop_size=prep_config["crop_size"])
    # print(prep_dict)

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    loss_config = config["loss"]
    # transfer_criterion = loss.loss_dict[loss_config["name"]]
    if "params" not in loss_config:
        loss_config["params"] = {}
    # print(transfer_criterion)
    transfer_criterion = DANLoss(**loss_config["params"])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    for data_config in config["data"]:
        name = data_config['name']
        dsets[name] = {}
        dset_loaders[name] = {}
        ## image data
        if data_config["type"] == "image":
            dsets[name]["train"] = ImageList(
                open(data_config["list_path"]["train"]).readlines(),
                transform=prep_dict[name]["train"])
            dset_loaders[name]["train"] = util_data.DataLoader(
                dsets[name]["train"],
                batch_size=data_config["batch_size"]["train"],
                shuffle=True,
                num_workers=4)
            if "test" in data_config["list_path"]:
                if prep_dict[name]["test_10crop"]:
                    for i in range(10):
                        dsets[name]["test" + str(i)] = ImageList(
                            open(data_config["list_path"]["test"]).readlines(),
                            transform=prep_dict[name]["test"]["val" + str(i)])
                        dset_loaders[name][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[name]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[name]["test"] = ImageList(
                        open(data_config["list_path"]["test"]).readlines(),
                        transform=prep_dict[name]["test"])
                    dset_loaders[name]["test"] = util_data.DataLoader(
                        dsets[name]["test"],
                        batch_size=data_config["batch_size"]["test"],
                        shuffle=False,
                        num_workers=4)
            else:
                if prep_dict[name]["test_10crop"]:
                    for i in range(10):
                        dsets[name]["test" + str(i)] = ImageList(
                            open(
                                data_config["list_path"]["train"]).readlines(),
                            transform=prep_dict[name]["test"]["val" + str(i)])
                        dset_loaders[name][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[name]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[name]["test"] = ImageList(
                        open(data_config["list_path"]["train"]).readlines(),
                        transform=prep_dict[name]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)

    class_num = 31

    ## set base network
    net_config = config["network"]
    base_network = network.network_dict[net_config["name"]]()
    if net_config["use_bottleneck"]:
        bottleneck_layer = nn.Linear(base_network.output_num(),
                                     net_config["bottleneck_dim"])
        classifier_layer = nn.Linear(bottleneck_layer.out_features, class_num)
    else:
        classifier_layer = nn.Linear(base_network.output_num(), class_num)

    ## initialization
    if net_config["use_bottleneck"]:
        bottleneck_layer.weight.data.normal_(0, 0.005)
        bottleneck_layer.bias.data.fill_(0.1)
        bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(),
                                         nn.Dropout(0.5))
    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)

    # print(base_network.state_dict())
    # print(classifier_layer.state_dict())

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        if net_config["use_bottleneck"]:
            bottleneck_layer = bottleneck_layer.to(device)
        classifier_layer = classifier_layer.to(device)
        base_network = base_network.to(device)

    ## collect parameters
    if net_config["use_bottleneck"]:
        parameter_list = [{
            "params": base_network.parameters(),
            "lr": 1
        }, {
            "params": bottleneck_layer.parameters(),
            "lr": 10
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    else:
        parameter_list = [{
            "params": base_network.parameters(),
            "lr": 1
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    ## add additional network for some methods
    if loss_config["name"] == "JAN":
        softmax_layer = nn.Softmax()
        if use_gpu:
            softmax_layer = softmax_layer.to(device)

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](
        parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]["train"]) - 1
    len_train_target = len(dset_loaders["target"]["train"]) - 1
    # transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    for i in range(config["num_iterations"]):
        # test in the train
        if i % config["test_interval"] == 0:
            base_network.train(False)
            classifier_layer.train(False)
            if net_config["use_bottleneck"]:
                bottleneck_layer.train(False)
                test_model = nn.Sequential(base_network, bottleneck_layer,
                                           classifier_layer)
                test_acc = image_classification_test(
                    dset_loaders["target"],
                    test_model,
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)
                print("iteration: %d, test accuracy: %f" % (i, test_acc))

            else:
                test_model = nn.Sequential(base_network, classifier_layer)
                test_acc = image_classification_test(
                    dset_loaders["target"],
                    test_model,
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)
                print("iteration: %d, test accuracy: %f" % (i, test_acc))
            # save model parameters
            if i % config["checkpoint_iterval"] == 0:
                torch.save(
                    test_model.state_dict(), config["checkpoint_dir"] +
                    "checkpoint_" + str(i).zfill(5) + ".pth")

        # loss_test = nn.BCELoss()
        # train one iter
        base_network.train(True)
        if net_config["use_bottleneck"]:
            bottleneck_layer.train(True)
        classifier_layer.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"]["train"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"]["train"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()

        inputs_source = inputs_source.to(device)
        inputs_target = inputs_target.to(device)
        labels_source = labels_source.to(device)

        inputs = torch.cat((inputs_source, inputs_target),
                           dim=0)  ### cat the source and target
        features = base_network(inputs)
        if net_config["use_bottleneck"]:
            features = bottleneck_layer(features)

        outputs = classifier_layer(features)

        # split the output for different loss
        num = inputs.size(0) // 2
        # the premise is the batch size of source and target is the same
        classifier_loss = class_criterion(outputs.narrow(0, 0, num),
                                          labels_source)
        ## switch between different transfer loss
        if loss_config["name"] == "DAN":
            # transfer_loss = transfer_criterion(features.narrow(0, 0, num),
            #                                    features.narrow(0, num, num),
            #                                    **loss_config["params"])

            transfer_loss = transfer_criterion(features.narrow(0, 0, num),
                                               features.narrow(0, num, num))
        elif loss_config["name"] == "RTN":
            ## RTN is still under developing
            transfer_loss = 0
        elif loss_config["name"] == "JAN":
            softmax_out = softmax_layer(outputs)
            transfer_loss = transfer_criterion([
                features.narrow(0, 0, num),
                softmax_out.narrow(0, 0, num)
            ], [features.narrow(0, num, num),
                softmax_out.narrow(0, num, num)], **loss_config["params"])

        total_loss = loss_config["trade_off"] * transfer_loss + classifier_loss
        if i % 100 == 0:
            print("iteration: ", str(i), "\t transfer loss: ",
                  str(transfer_loss.item()), "\t classification loss: ",
                  str(classifier_loss.item()), "\t total loss: ",
                  str(total_loss.item()))
            for param_group in optimizer.param_groups:
                print("lr: ", param_group["lr"])
            # log for losses
            writer.add_scalar('Train/loss_classification',
                              classifier_loss.item(), i // 100)
            writer.add_scalar('Train/loss_transfer', transfer_loss.item(),
                              i // 100)
            writer.add_scalar('Train/loss_total', total_loss.item(), i // 100)
        total_loss.backward()
        optimizer.step()
コード例 #15
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    prep_dict["target"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    else:
        prep_dict["test"] = prep.image_test( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    transfer_criterion = loss.PADA
    loss_params = config["loss"]

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = util_data.DataLoader(dsets["source"], \
            batch_size=data_config["source"]["batch_size"], \
            shuffle=True, num_workers=4)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = util_data.DataLoader(dsets["target"], \
            batch_size=data_config["target"]["batch_size"], \
            shuffle=True, num_workers=4)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"+str(i)] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["test"+str(i)] = util_data.DataLoader(dsets["test"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

            dsets["target"+str(i)] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["target"+str(i)] = util_data.DataLoader(dsets["target"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = util_data.DataLoader(dsets["test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

        dsets["target_test"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["target_test"] = MyDataLoader(dsets["target_test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["params"]["new_cls"]:
        if net_config["params"]["use_bottleneck"]:
            parameter_list = [{"params":base_network.feature_layers.parameters(), "lr":1}, \
                            {"params":base_network.bottleneck.parameters(), "lr":10}, \
                            {"params":base_network.fc.parameters(), "lr":10}]
        else:
            parameter_list = [{"params":base_network.feature_layers.parameters(), "lr":1}, \
                            {"params":base_network.fc.parameters(), "lr":10}]
    else:
        parameter_list = [{"params": base_network.parameters(), "lr": 1}]

    ## add additional network for some methods
    class_weight = torch.from_numpy(np.array([1.0] * class_num))
    if use_gpu:
        class_weight = class_weight.cuda()
    ad_net = network.AdversarialNetwork(base_network.output_num())
    gradient_reverse_layer = network.AdversarialLayer(
        high_value=config["high"])
    if use_gpu:
        ad_net = ad_net.cuda()
    parameter_list.append({"params": ad_net.parameters(), "lr": 10})

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]) - 1
    len_train_target = len(dset_loaders["target"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == 0:
            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders, \
                base_network, test_10crop=prep_config["test_10crop"], \
                gpu=use_gpu)
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str)
            config["out_file"].flush()
            print(log_str)
        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                "iter_{:05d}_model.pth.tar".format(i)))

        ## train one iter
        base_network.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = \
                Variable(inputs_source).cuda(), Variable(inputs_target).cuda(), \
                Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(inputs_source), \
                Variable(inputs_target), Variable(labels_source)

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features, outputs = base_network(inputs)

        softmax_out = nn.Softmax(dim=1)(outputs).detach()
        ad_net.train(True)
        transfer_loss = transfer_criterion(features, ad_net,
                                           gradient_reverse_layer, use_gpu)

        classifier_loss = class_criterion(
            outputs.narrow(0, 0,
                           inputs.size(0) / 2), labels_source)

        total_loss = loss_params["trade_off"] * transfer_loss + classifier_loss
        total_loss.backward()
        optimizer.step()
    torch.save(best_model, osp.join(config["output_path"],
                                    "best_model.pth.tar"))
    return best_acc
コード例 #16
0
def transfer_classification(config, name):
    ## set pre-process
    prep_dict = {}
    for prep_config in config["prep"]:
        prep_dict[prep_config["name"]] = {}
        if prep_config["type"] == "image":
            prep_dict[prep_config["name"]]["test_10crop"] = prep_config[
                "test_10crop"]
            prep_dict[prep_config["name"]]["train"] = prep.image_train(
                resize_size=prep_config["resize_size"],
                crop_size=prep_config["crop_size"])
            if prep_config["test_10crop"]:
                prep_dict[
                    prep_config["name"]]["test"] = prep.image_test_10crop(
                        resize_size=prep_config["resize_size"],
                        crop_size=prep_config["crop_size"])
            else:
                prep_dict[prep_config["name"]]["test"] = prep.image_test(
                    resize_size=prep_config["resize_size"],
                    crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    loss_config = config["loss"]
    transfer_criterion = loss.loss_dict[loss_config["name"]]
    if "params" not in loss_config:
        loss_config["params"] = {}

    ## prepare data
    dsets = {}
    dset_loaders = {}
    for data_config in config["data"]:
        dsets[data_config["name"]] = {}
        dset_loaders[data_config["name"]] = {}
        ## image data
        if data_config["type"] == "image":
            # dsets[data_config["name"]]["train"]为ImageList类,其中含有source中数据及标签和预处理过程
            dsets[data_config["name"]]["train"] = ImageList(
                open(data_config["list_path"]["train"]).readlines(),
                transform=prep_dict[data_config["name"]]["train"])
            # dset_loaders含有数据batchsize信息等
            dset_loaders[data_config["name"]]["train"] = util_data.DataLoader(
                dsets[data_config["name"]]["train"],
                batch_size=data_config["batch_size"]["train"],
                shuffle=True,
                num_workers=4)
            if "test" in data_config["list_path"]:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["test"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["test"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)
            else:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["train"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["train"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)
    class_num = 12

    ## set base network
    net_config = config["network"]
    base_network = network.network_dict[net_config["name"]]()
    if net_config["use_bottleneck"]:
        bottleneck_layer = nn.Linear(base_network.output_num(),
                                     net_config["bottleneck_dim"])
        classifier_layer = nn.Linear(bottleneck_layer.out_features, class_num)
    else:
        print 'outputnum:', base_network.output_num()
        classifier_layer = nn.Linear(base_network.output_num(), class_num)

    ## initialization
    if net_config["use_bottleneck"]:
        # 初始化bottlenect层weight
        bottleneck_layer.weight.data.normal_(0, 0.005)
        bottleneck_layer.bias.data.fill_(0.1)
        # nn.sequential按次序封装层
        bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(),
                                         nn.Dropout(0.5))
    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        if net_config["use_bottleneck"]:
            bottleneck_layer = bottleneck_layer.cuda()
        classifier_layer = classifier_layer.cuda()
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["use_bottleneck"]:
        parameter_list = [{
            "params": base_network.parameters(),
            "lr": 1
        }, {
            "params": bottleneck_layer.parameters(),
            "lr": 10
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    else:
        parameter_list = [{
            "params": base_network.parameters(),
            "lr": 1
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    ## add additional network for some methods
    if loss_config["name"] == "JAN":
        softmax_layer = nn.Softmax()
        if use_gpu:
            softmax_layer = softmax_layer.cuda()

    ## set optimizer
    optimizer_config = config["optimizer"]
    # optimizer初始化了所有权重
    optimizer = optim_dict[optimizer_config["type"]](
        parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]["train"]) - 1
    len_train_target = len(dset_loaders["target"]["train"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    max_accuracy = 0
    for i in range(config["num_iterations"] + 1):
        ## test in the train
        if i % config["test_interval"] == 0 and i != 0:
            base_network.train(False)
            classifier_layer.train(False)

            if net_config["use_bottleneck"]:
                bottleneck_layer.train(False)

                accuracy = image_classification_test(
                    dset_loaders["target"],
                    nn.Sequential(base_network, bottleneck_layer,
                                  classifier_layer),
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)

                torch.save(base_network,
                           '../save/nobottle_base_network_' + name + '.pkl')
                torch.save(
                    classifier_layer,
                    '../save/nobottle_classifier_layer_' + name + '.pkl')
                print 'save', i
                if (accuracy > max_accuracy):
                    max_accuracy = accuracy
                print 'iter{0}accuracy:'.format(
                    i), accuracy, 'max_accuracy:', max_accuracy

            else:

                torch.save(base_network,
                           '../save/nobottle_base_network_' + name + '.pkl')
                torch.save(
                    classifier_layer,
                    '../save/nobottle_classifier_layer_' + name + '.pkl')
                print 'save', i
                accuracy = image_classification_test(
                    dset_loaders["target"],
                    nn.Sequential(base_network, classifier_layer),
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)
                if (accuracy > max_accuracy):
                    max_accuracy = accuracy
                print 'iter{0}accuracy:'.format(
                    i), accuracy, 'max_accuracy:', max_accuracy

        loss_test = nn.BCELoss()
        ## train one iter
        base_network.train(True)
        if net_config["use_bottleneck"]:
            bottleneck_layer.train(True)
        classifier_layer.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"]["train"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"]["train"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source).cuda(), Variable(
                    inputs_target).cuda(), Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source), Variable(inputs_target), Variable(
                    labels_source)

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features = base_network(inputs)
        if net_config["use_bottleneck"]:
            features = bottleneck_layer(features)

        outputs = classifier_layer(features)

        classifier_loss = class_criterion(
            outputs.narrow(0, 0,
                           inputs.size(0) / 2), labels_source)
        total_loss = classifier_loss
        total_loss.backward()
        optimizer.step()
コード例 #17
0
ファイル: train.py プロジェクト: zhangzhao156/Xlearn
def transfer_classification(config):
    ## set pre-process
    prep_dict = {}
    for prep_config in config["prep"]:
        prep_dict[prep_config["name"]] = {}
        if prep_config["type"] == "image":
            prep_dict[prep_config["name"]]["test_10crop"] = prep_config[
                "test_10crop"]
            prep_dict[prep_config["name"]]["train"] = prep.image_train(
                resize_size=prep_config["resize_size"],
                crop_size=prep_config["crop_size"])
            if prep_config["test_10crop"]:
                prep_dict[
                    prep_config["name"]]["test"] = prep.image_test_10crop(
                        resize_size=prep_config["resize_size"],
                        crop_size=prep_config["crop_size"])
            else:
                prep_dict[prep_config["name"]]["test"] = prep.image_test(
                    resize_size=prep_config["resize_size"],
                    crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    loss_config = config["loss"]
    transfer_criterion = loss.loss_dict[loss_config["name"]]
    if "params" not in loss_config:
        loss_config["params"] = {}

    ## prepare data
    dsets = {}
    dset_loaders = {}
    for data_config in config["data"]:
        dsets[data_config["name"]] = {}
        dset_loaders[data_config["name"]] = {}
        ## image data
        if data_config["type"] == "image":
            dsets[data_config["name"]]["train"] = ImageList(
                open(data_config["list_path"]["train"]).readlines(),
                transform=prep_dict[data_config["name"]]["train"])
            dset_loaders[data_config["name"]]["train"] = util_data.DataLoader(
                dsets[data_config["name"]]["train"],
                batch_size=data_config["batch_size"]["train"],
                shuffle=True,
                num_workers=4)
            if "test" in data_config["list_path"]:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["test"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["test"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)
            else:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["train"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["train"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)
    class_num = 31

    ## set base network
    net_config = config["network"]
    base_network = network.network_dict[net_config["name"]]()
    if net_config["use_bottleneck"]:
        bottleneck_layer = nn.Linear(base_network.output_num(),
                                     net_config["bottleneck_dim"])
        classifier_layer = nn.Linear(bottleneck_layer.out_features, class_num)
    else:
        classifier_layer = nn.Linear(base_network.output_num(), class_num)
    for param in base_network.parameters():
        param.requires_grad = False

    ## initialization
    if net_config["use_bottleneck"]:
        bottleneck_layer.weight.data.normal_(0, 0.005)
        bottleneck_layer.bias.data.fill_(0.1)
        bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(),
                                         nn.Dropout(0.5))
    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        if net_config["use_bottleneck"]:
            bottleneck_layer = bottleneck_layer.cuda()
        classifier_layer = classifier_layer.cuda()
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["use_bottleneck"]:
        parameter_list = [{
            "params": bottleneck_layer.parameters(),
            "lr": 10
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    else:
        parameter_list = [{"params": classifier_layer.parameters(), "lr": 10}]

    ## add additional network for some methods
    if loss_config["name"] == "JAN":
        softmax_layer = nn.Softmax()
        if use_gpu:
            softmax_layer = softmax_layer.cuda()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](
        parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]["train"]) - 1
    len_train_target = len(dset_loaders["target"]["train"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    for i in range(config["num_iterations"]):
        ## test in the train
        if i % config["test_interval"] == 0:
            base_network.train(False)
            classifier_layer.train(False)
            if net_config["use_bottleneck"]:
                bottleneck_layer.train(False)
                print image_classification_test(
                    dset_loaders["target"],
                    nn.Sequential(base_network, bottleneck_layer,
                                  classifier_layer),
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)

            else:
                print image_classification_test(
                    dset_loaders["target"],
                    nn.Sequential(base_network, classifier_layer),
                    test_10crop=prep_dict["target"]["test_10crop"],
                    gpu=use_gpu)

        loss_test = nn.BCELoss()
        ## train one iter
        if net_config["use_bottleneck"]:
            bottleneck_layer.train(True)
        classifier_layer.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"]["train"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"]["train"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source).cuda(), Variable(
                    inputs_target).cuda(), Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source), Variable(inputs_target), Variable(
                    labels_source)

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features = base_network(inputs)
        if net_config["use_bottleneck"]:
            features = bottleneck_layer(features)

        outputs = classifier_layer(features)

        classifier_loss = class_criterion(
            outputs.narrow(0, 0,
                           inputs.size(0) / 2), labels_source)
        ## switch between different transfer loss
        if loss_config["name"] == "DAN":
            transfer_loss = transfer_criterion(
                features.narrow(0, 0,
                                features.size(0) / 2),
                features.narrow(0,
                                features.size(0) / 2,
                                features.size(0) / 2), **loss_config["params"])
        elif loss_config["name"] == "RTN":
            ## RTN is still under developing
            transfer_loss = 0
        elif loss_config["name"] == "JAN":
            softmax_out = softmax_layer(outputs)
            transfer_loss = transfer_criterion([
                features.narrow(0, 0,
                                features.size(0) / 2),
                softmax_out.narrow(0, 0,
                                   softmax_out.size(0) / 2)
            ], [
                features.narrow(0,
                                features.size(0) / 2,
                                features.size(0) / 2),
                softmax_out.narrow(0,
                                   softmax_out.size(0) / 2,
                                   softmax_out.size(0) / 2)
            ], **loss_config["params"])

        total_loss = loss_config["trade_off"] * transfer_loss + classifier_loss
        total_loss.backward()
        optimizer.step()
コード例 #18
0
def transfer_classification(config):
	## set pre-process
	prep_dict = {}
	for prep_config in config["prep"]:
		prep_dict[prep_config["name"]] = {}
		if prep_config["type"] == "image":
		    prep_dict[prep_config["name"]]["test_10crop"] = prep_config["test_10crop"]
		    prep_dict[prep_config["name"]]["train"]  = prep.image_train(resize_size=prep_config["resize_size"], crop_size=prep_config["crop_size"])
		    if prep_config["test_10crop"]:
		        prep_dict[prep_config["name"]]["validation"] = prep.image_test_10crop(resize_size=prep_config["resize_size"], crop_size=prep_config["crop_size"])
		    else:
		        prep_dict[prep_config["name"]]["validation"] = prep.image_test(resize_size=prep_config["resize_size"], crop_size=prep_config["crop_size"])

	print("Data preprocessing done..........::")
	## set loss
	class_criterion = nn.CrossEntropyLoss()
	loss_config = config["loss"]
	transfer_criterion = loss.loss_dict[loss_config["name"]]
	if "params" not in loss_config:
		loss_config["params"] = {}
	print("Setting loss done...............::")
	print("Data Preparation progressing................::")

	## prepare data
	dsets = {}
	dset_loaders = {}
	for data_config in config["data"]:
		dsets[data_config["name"]] = {}
		dset_loaders[data_config["name"]] = {}
		## image data
		if data_config["type"] == "image":
		    dsets[data_config["name"]]["train"] = ImageList(open(data_config["list_path"]["train"]).readlines(), transform=prep_dict[data_config["name"]]["train"])
		    dset_loaders[data_config["name"]]["train"] = util_data.DataLoader(dsets[data_config["name"]]["train"], batch_size=data_config["batch_size"]["train"], shuffle=True, num_workers=2)
		    if "validation" in data_config["list_path"]:
		        if prep_dict[data_config["name"]]["test_10crop"]:
		            for i in range(10):
		                dsets[data_config["name"]]["validation"+str(i)] = ImageList(open(data_config["list_path"]["validation"]).readlines(), transform=prep_dict[data_config["name"]]["validation"]["val"+str(i)])
		                dset_loaders[data_config["name"]]["validation"+str(i)] = util_data.DataLoader(dsets[data_config["name"]]["validation"+str(i)], batch_size=data_config["batch_size"]["validation"], shuffle=False, num_workers=2)
		        else:
		            dsets[data_config["name"]]["validation"] = ImageList(open(data_config["list_path"]["validation"]).readlines(), transform=prep_dict[data_config["name"]]["validation"])
		            dset_loaders[data_config["name"]]["validation"] = util_data.DataLoader(dsets[data_config["name"]]["validation"], batch_size=data_config["batch_size"]["validation"], shuffle=False, num_workers=4)
	class_num = 2
	print("Data prepration done.....::")
	print("Setting base network......::")
	## set base network
	net_config = config["network"]
	base_network = network.network_dict[net_config["name"]]()
	if net_config["use_bottleneck"]:
		bottleneck_layer = nn.Linear(base_network.output_num(), 256)
		# bottleneck_layer_1 = nn.Linear(256, 64)
		classifier_layer = nn.Linear(256, class_num)
	else:
		classifier_layer = nn.Linear(base_network.output_num(), class_num)
	for param in base_network.parameters():
		param.requires_grad = True
	print("Base network set......::")
	print("Intilializing bottleneck layer....::")

	## initialization
	if net_config["use_bottleneck"]:
		bottleneck_layer.weight.data.normal_(0, 0.1)
		bottleneck_layer.bias.data.fill_(0.1)
		bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(), nn.Dropout(0.2))
		# bottleneck_layer_1.weight.data.normal_(0, 0.1)
		# bottleneck_layer_1.bias.data.fill_(0.1)
		# bottleneck_layer_1 = nn.Sequential(bottleneck_layer_1, nn.ReLU(), nn.Dropout(0.2))
	classifier_layer.weight.data.normal_(0, 0.01)
	classifier_layer.bias.data.fill_(0.0)

	use_gpu = torch.cuda.is_available()
	# use_gpu = False
	if use_gpu:
		if net_config["use_bottleneck"]:
		    bottleneck_layer = bottleneck_layer.cuda()
		    # bottleneck_layer_1 = bottleneck_layer_1.cuda()
		classifier_layer = classifier_layer.cuda()
		base_network = base_network.cuda()

	print("Collect parameters.......")


	## collect parameters
	if net_config["use_bottleneck"]:
		parameter_list = [{"params":bottleneck_layer.parameters(), "lr":0.1}, {"params":classifier_layer.parameters(), "lr":0.1}]

	else:
		parameter_list = [{"params":classifier_layer.parameters(), "lr":1.0}]

	## add additional network for some methods
	if loss_config["name"] == "JAN":
		softmax_layer = nn.Softmax()
		if use_gpu:
		    softmax_layer = softmax_layer.cuda()

	print("set optimizer.....::")


	## set optimizer
	optimizer_config = config["optimizer"]
	optimizer = optim_dict[optimizer_config["type"]](parameter_list, **(optimizer_config["optim_params"]))
	param_lr = []
	for param_group in optimizer.param_groups:
		param_lr.append(param_group["lr"])
	schedule_param = optimizer_config["lr_param"]
	lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

	print("Training progress......::")
	## train   =
	len_train_source = len(dset_loaders["source"]["train"]) - 1
	len_train_target = len(dset_loaders["target"]["train"]) - 1
	transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
	running_loss = 0.0
	for i in range(config["num_iterations"]):
		## test in the train
		# print("iteration::", i)
		if i % config["test_interval"] == 0 or i < 10:
		    base_network.train(False)
		    classifier_layer.train(False)
		    if net_config["use_bottleneck"]:
		        bottleneck_layer.train(False)
		        # bottleneck_layer_1.train(False)
		        print("Validation Accuracy:::", image_classification_test(dset_loaders["target"], nn.Sequential(base_network, bottleneck_layer, classifier_layer), test_10crop=prep_dict["target"]["test_10crop"], gpu=use_gpu))

		    else:
		        print ("Validation Accuracy:::", image_classification_test(dset_loaders["target"], nn.Sequential(base_network, classifier_layer), test_10crop=prep_dict["target"]["test_10crop"], gpu=use_gpu))

		loss_test = nn.BCELoss()
		## train one iter
		# base_network.train(True)
		if net_config["use_bottleneck"]:
		    bottleneck_layer.train(True)
		    # bottleneck_layer_1.train(True)
		classifier_layer.train(True)
		optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
		optimizer.zero_grad()
		if i % len_train_source == 0:
		    iter_source = iter(dset_loaders["source"]["train"])
		if i % len_train_target == 0:
		    iter_target = iter(dset_loaders["target"]["train"])
		inputs_source, labels_source = iter_source.next()
		inputs_target, labels_target = iter_target.next()
		if use_gpu:
		    inputs_source, inputs_target, labels_source = Variable(inputs_source).cuda(), Variable(inputs_target).cuda(), Variable(labels_source).cuda()
		else:
		    inputs_source, inputs_target, labels_source = Variable(inputs_source), Variable(inputs_target), Variable(labels_source)
		# print("source::",inputs_source)
		# print("target::", inputs_target)
		# print("label source::", labels_source)
		# print("labels target::", labels_target)

		inputs = torch.cat((inputs_source, inputs_target), dim=0)
		features_ = base_network(inputs)
		# print("********Base network features*******::", features_)
		# sys.exit(0)
		if net_config["use_bottleneck"]:
		    features = bottleneck_layer(features_)
		    # features = bottleneck_layer_1(features_1)
		# print("*****features from bottleneck layer*****", features)
		outputs = classifier_layer(features)
		# print("***output****", outputs)
		#print("Inputs size::",inputs.size(0)/2)

		classifier_loss = class_criterion(outputs.narrow(0, 0, int(inputs.size(0)/2)), labels_source)
		## switch between different transfer loss
		if loss_config["name"] == "DAN":
		    transfer_loss = transfer_criterion(features.narrow(0, 0, int(features.size(0)/2)), features.narrow(0, int(features.size(0)/2), int(features.size(0)/2)), **loss_config["params"])
		elif loss_config["name"] == "RTN":
		    ## RTN is still under developing
		    transfer_loss = 0
		elif loss_config["name"] == "JAN":
		    softmax_out = softmax_layer(outputs)
		    transfer_loss = transfer_criterion([features.narrow(0, 0, int(features.size(0)/2)), softmax_out.narrow(0, 0, int(softmax_out.size(0)/2))], [features.narrow(0, int(features.size(0)/2), int(features.size(0)/2)), softmax_out.narrow(0, int(softmax_out.size(0)/2), int(softmax_out.size(0)/2))], **loss_config["params"])

		total_loss = loss_config["trade_off"] * transfer_loss + classifier_loss
		running_loss += total_loss.data.cpu().numpy()
		total_loss.backward()
		optimizer.step()
		if i % config["test_interval"] == 0 or i<10:
		    if i == 0:
		        print("Training loss at iteration {} is {}".format(i, (running_loss)))
		    else:
		        print("Training loss at iteration {} is {}".format(i, (running_loss/i)))
		    if net_config["use_bottleneck"]:
		        model = nn.Sequential(base_network, bottleneck_layer, classifier_layer)
		    else:
		        model = nn.Sequential(base_network, classifier_layer)
		    torch.save(model.state_dict(), "./weights_sp/r18_epoch_{}.pt".format(i))
コード例 #19
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    tensor_writer = SummaryWriter(config["tensorboard_path"])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]

    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                shuffle=False, num_workers=4) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.cuda()
    parameter_list = base_network.get_parameters()
 
    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        base_network = nn.DataParallel(base_network, device_ids=[int(i) for i in gpus])

    ## train   
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == config["test_interval"] - 1 or i==0:
            base_network.train(False)
            temp_acc, output, prediction, label, feature = image_classification_test(dset_loaders, \
                base_network, test_10crop=prep_config["test_10crop"])
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str+"\n")
            config["out_file"].flush()
            print(log_str)
        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                "iter_{:05d}_model.pth.tar".format(i)))

        loss_params = config["loss"]                  
        ## train one iter
        base_network.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)

        outputs_target_temp = outputs_target / config['temperature']
        target_softmax_out_temp = nn.Softmax(dim=1)(outputs_target_temp)
        target_entropy_weight = loss.Entropy(target_softmax_out_temp).detach()
        target_entropy_weight = 1 + torch.exp(-target_entropy_weight)
        target_entropy_weight = train_bs * target_entropy_weight / torch.sum(target_entropy_weight)
        cov_matrix_t = target_softmax_out_temp.mul(target_entropy_weight.view(-1,1)).transpose(1,0).mm(target_softmax_out_temp)
        cov_matrix_t = cov_matrix_t / torch.sum(cov_matrix_t, dim=1)
        mcc_loss = (torch.sum(cov_matrix_t) - torch.trace(cov_matrix_t)) / class_num

        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
        total_loss = classifier_loss + mcc_loss
        total_loss.backward()
        optimizer.step()

        tensor_writer.add_scalar('total_loss', total_loss, i)
        tensor_writer.add_scalar('classifier_loss', classifier_loss, i)
        tensor_writer.add_scalar('cov_matrix_penalty', mcc_loss, i)

    torch.save(best_model, osp.join(config["output_path"], "best_model.pth.tar"))
    return best_acc
コード例 #20
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]

    source_list = [
        '.' + i for i in open(data_config["source"]["list_path"]).readlines()
    ]
    target_list = [
        '.' + i for i in open(data_config["target"]["list_path"]).readlines()
    ]

    dsets["source"] = ImageList(source_list, \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
            shuffle=True, num_workers=config['args'].num_worker, drop_last=True)
    dsets["target"] = ImageList(target_list, \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
            shuffle=True, num_workers=config['args'].num_worker, drop_last=True)
    print("source dataset len:", len(dsets["source"]))
    print("target dataset len:", len(dsets["target"]))

    if prep_config["test_10crop"]:
        for i in range(10):
            test_list = [
                '.' + i
                for i in open(data_config["test"]["list_path"]).readlines()
            ]
            dsets["test"] = [ImageList(test_list, \
                                transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                shuffle=False, num_workers=config['args'].num_worker) for dset in dsets['test']]
    else:
        test_list = [
            '.' + i
            for i in open(data_config["test"]["list_path"]).readlines()
        ]
        dsets["test"] = ImageList(test_list, \
                                transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                shuffle=False, num_workers=config['args'].num_worker)

    dsets["target_label"] = ImageList_label(target_list, \
                            transform=prep_dict["target"])
    dset_loaders["target_label"] = DataLoader(dsets["target_label"], batch_size=test_bs, \
            shuffle=False, num_workers=config['args'].num_worker, drop_last=False)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.to(network.dev)
    if config["restore_path"]:
        checkpoint = torch.load(
            osp.join(config["restore_path"], "best_model.pth"))["base_network"]
        ckp = {}
        for k, v in checkpoint.items():
            if "module" in k:
                ckp[k.split("module.")[-1]] = v
            else:
                ckp[k] = v
        base_network.load_state_dict(ckp)
        log_str = "successfully restore from {}".format(
            osp.join(config["restore_path"], "best_model.pth"))
        config["out_file"].write(log_str + "\n")
        config["out_file"].flush()
        print(log_str)

    ## add additional network for some methods
    if "ALDA" in args.method:
        ad_net = network.Multi_AdversarialNetwork(base_network.output_num(),
                                                  1024, class_num)
    else:
        ad_net = network.AdversarialNetwork(base_network.output_num(), 1024)
    ad_net = ad_net.to(network.dev)
    parameter_list = base_network.get_parameters() + ad_net.get_parameters()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        ad_net = nn.DataParallel(ad_net,
                                 device_ids=[int(i) for i in range(len(gpus))])
        base_network = nn.DataParallel(
            base_network, device_ids=[int(i) for i in range(len(gpus))])

    loss_params = config["loss"]
    high = loss_params["trade_off"]
    begin_label = False
    writer = SummaryWriter(config["output_path"])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    loss_value = 0
    loss_adv_value = 0
    loss_correct_value = 0
    for i in tqdm(range(config["num_iterations"]),
                  total=config["num_iterations"]):
        if i % config["test_interval"] == config["test_interval"] - 1:
            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders, \
                base_network, test_10crop=prep_config["test_10crop"])
            temp_model = base_network  #nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_step = i
                best_acc = temp_acc
                best_model = temp_model
                checkpoint = {
                    "base_network": best_model.state_dict(),
                    "ad_net": ad_net.state_dict()
                }
                torch.save(checkpoint,
                           osp.join(config["output_path"], "best_model.pth"))
                print(
                    "\n##########     save the best model.    #############\n")
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()
            writer.add_scalar('precision', temp_acc, i)
            print(log_str)

            print("adv_loss: {:.3f} correct_loss: {:.3f} class_loss: {:.3f}".
                  format(loss_adv_value, loss_correct_value, loss_value))
            loss_value = 0
            loss_adv_value = 0
            loss_correct_value = 0

            #show val result on tensorboard
            images_inv = prep.inv_preprocess(inputs_source.clone().cpu(), 3)
            for index, img in enumerate(images_inv):
                writer.add_image(str(index) + '/Images', img, i)

        # save the pseudo_label
        if 'PseudoLabel' in config['method'] and (
                i % config["label_interval"] == config["label_interval"] - 1):
            base_network.train(False)
            pseudo_label_list = image_label(dset_loaders, base_network, threshold=config['threshold'], \
                                out_dir=config["output_path"])
            dsets["target"] = ImageList(open(pseudo_label_list).readlines(), \
                                transform=prep_dict["target"])
            dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                    shuffle=True, num_workers=config['args'].num_worker, drop_last=True)
            iter_target = iter(
                dset_loaders["target"]
            )  # replace the target dataloader with Pseudo_Label dataloader
            begin_label = True

        if i > config["stop_step"]:
            log_str = "method {}, iter: {:05d}, precision: {:.5f}".format(
                config["output_path"], best_step, best_acc)
            config["final_log"].write(log_str + "\n")
            config["final_log"].flush()
            break

        ## train one iter
        base_network.train(True)
        ad_net.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = Variable(
            inputs_source).to(network.dev), Variable(inputs_target).to(
                network.dev), Variable(labels_source).to(network.dev)
        features_source, outputs_source = base_network(inputs_source)
        if args.source_detach:
            features_source = features_source.detach()
        features_target, outputs_target = base_network(inputs_target)
        features = torch.cat((features_source, features_target), dim=0)
        outputs = torch.cat((outputs_source, outputs_target), dim=0)
        softmax_out = nn.Softmax(dim=1)(outputs)
        loss_params["trade_off"] = network.calc_coeff(
            i, high=high)  #if i > 500 else 0.0
        transfer_loss = 0.0
        if 'DANN' in config['method']:
            transfer_loss = loss.DANN(features, ad_net)
        elif "ALDA" in config['method']:
            ad_out = ad_net(features)
            adv_loss, reg_loss, correct_loss = loss.ALDA_loss(
                ad_out,
                labels_source,
                softmax_out,
                weight_type=config['args'].weight_type,
                threshold=config['threshold'])
            # whether add the corrected self-training loss
            if "nocorrect" in config['args'].loss_type:
                transfer_loss = adv_loss
            else:
                transfer_loss = config['args'].adv_weight * adv_loss + config[
                    'args'].adv_weight * loss_params["trade_off"] * correct_loss
            # reg_loss is only backward to the discriminator
            if "noreg" not in config['args'].loss_type:
                for param in base_network.parameters():
                    param.requires_grad = False
                reg_loss.backward(retain_graph=True)
                for param in base_network.parameters():
                    param.requires_grad = True
        # on-line self-training
        elif 'SelfTraining' in config['method']:
            transfer_loss += loss_params["trade_off"] * loss.SelfTraining_loss(
                outputs, softmax_out, config['threshold'])
        # off-line self-training
        elif 'PseudoLabel' in config['method']:
            labels_target = labels_target.to(network.dev)
            if begin_label:
                transfer_loss += loss_params["trade_off"] * nn.CrossEntropyLoss(
                    ignore_index=-1)(outputs_target, labels_target)
            else:
                transfer_loss += 0.0 * nn.CrossEntropyLoss(ignore_index=-1)(
                    outputs_target, labels_target)

        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
        loss_value += classifier_loss.item() / config["test_interval"]
        loss_adv_value += adv_loss.item() / config["test_interval"]
        loss_correct_value += correct_loss.item() / config["test_interval"]
        total_loss = classifier_loss + transfer_loss
        total_loss.backward()
        optimizer.step()
    checkpoint = {
        "base_network": temp_model.state_dict(),
        "ad_net": ad_net.state_dict()
    }
    torch.save(checkpoint, osp.join(config["output_path"], "final_model.pth"))
    return best_acc
コード例 #21
0
def transfer_classification(config):
    ## set pre-process
    prep_dict = {}
    for prep_config in config["prep"]:
        prep_dict[prep_config["name"]] = {}
        if prep_config["type"] == "image":
            prep_dict[prep_config["name"]]["test_10crop"] = prep_config[
                "test_10crop"]
            prep_dict[prep_config["name"]]["train"] = prep.image_train(
                resize_size=prep_config["resize_size"],
                crop_size=prep_config["crop_size"])
            if prep_config["test_10crop"]:
                prep_dict[
                    prep_config["name"]]["test"] = prep.image_test_10crop(
                        resize_size=prep_config["resize_size"],
                        crop_size=prep_config["crop_size"])
            else:
                prep_dict[prep_config["name"]]["test"] = prep.image_test(
                    resize_size=prep_config["resize_size"],
                    crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    loss_config = config["loss"]
    transfer_criterion = loss.loss_dict[loss_config["name"]]
    if "params" not in loss_config:
        loss_config["params"] = {}

    ## prepare data
    dsets = {}
    dset_loaders = {}
    for data_config in config["data"]:
        dsets[data_config["name"]] = {}
        dset_loaders[data_config["name"]] = {}
        ## image data
        if data_config["type"] == "image":
            dsets[data_config["name"]]["train"] = ImageList(
                open(data_config["list_path"]["train"]).readlines(),
                transform=prep_dict[data_config["name"]]["train"])
            dset_loaders[data_config["name"]]["train"] = util_data.DataLoader(
                dsets[data_config["name"]]["train"],
                batch_size=data_config["batch_size"]["train"],
                shuffle=True,
                num_workers=4)
            if "test" in data_config["list_path"]:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["test"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["test"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)
            else:
                if prep_dict[data_config["name"]]["test_10crop"]:
                    for i in range(10):
                        dsets[data_config["name"]][
                            "test" + str(i)] = ImageList(
                                open(data_config["list_path"]
                                     ["train"]).readlines(),
                                transform=prep_dict[data_config["name"]]
                                ["test"]["val" + str(i)])
                        dset_loaders[data_config["name"]][
                            "test" + str(i)] = util_data.DataLoader(
                                dsets[data_config["name"]]["test" + str(i)],
                                batch_size=data_config["batch_size"]["test"],
                                shuffle=False,
                                num_workers=4)
                else:
                    dsets[data_config["name"]]["test"] = ImageList(
                        open(data_config["list_path"]["train"]).readlines(),
                        transform=prep_dict[data_config["name"]]["test"])
                    dset_loaders[
                        data_config["name"]]["test"] = util_data.DataLoader(
                            dsets[data_config["name"]]["test"],
                            batch_size=data_config["batch_size"]["test"],
                            shuffle=False,
                            num_workers=4)

    class_num = config["classnum"]

    ## set base network
    net_config = config["network"]
    base_network = network.network_dict[net_config["name"]]()
    if net_config["DAN2"]:
        fc7 = nn.Sequential(nn.ReLU(True), nn.Dropout(), nn.Linear(4096, 4096))
        fc7_relu = nn.Sequential(nn.ReLU(True), nn.Dropout())
    if net_config["use_bottleneck"]:
        bottleneck_layer = nn.Linear(base_network.output_num(),
                                     net_config["bottleneck_dim"])
        classifier_layer = nn.Linear(bottleneck_layer.out_features, class_num)
    else:
        classifier_layer = nn.Linear(base_network.output_num(), class_num)
    for param in base_network.parameters():
        param.requires_grad = False

    ## initialization
    if net_config["use_bottleneck"]:
        bottleneck_layer.weight.data.normal_(0, 0.005)
        bottleneck_layer.bias.data.fill_(0.1)
        bottleneck_layer = nn.Sequential(bottleneck_layer, nn.ReLU(),
                                         nn.Dropout(0.5))

    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)

    use_gpu = config["use_gpu"]

    if use_gpu:
        if net_config["use_bottleneck"]:
            bottleneck_layer = bottleneck_layer.cuda()

        if net_config["DAN2"]:
            fc7 = fc7.cuda()
            fc7_relu = fc7_relu.cuda()

        classifier_layer = classifier_layer.cuda()
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["use_bottleneck"]:
        parameter_list = [{
            "params": bottleneck_layer.parameters(),
            "lr": 10
        }, {
            "params": classifier_layer.parameters(),
            "lr": 10
        }]

    else:
        parameter_list = [{"params": classifier_layer.parameters(), "lr": 10}]

    ## add additional network for some methods
    if loss_config["name"] == "JAN":
        softmax_layer = nn.Softmax()
        if use_gpu:
            softmax_layer = softmax_layer.cuda()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](
        parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]["train"]) - 1
    len_train_target = len(dset_loaders["target"]["train"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0

    ## Quyan::HERE needs to add mini-batch------------------------------------------------------------------------------------------------------------------------
    for i in range(config["num_iterations"]):
        ## train one iter
        if net_config["use_bottleneck"]:
            bottleneck_layer.train(True)
        classifier_layer.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"]["train"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"]["train"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source).cuda(), Variable(
                    inputs_target).cuda(), Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(
                inputs_source), Variable(inputs_target), Variable(
                    labels_source)

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features = base_network(inputs)
        if net_config["use_bottleneck"]:
            features = bottleneck_layer(features)

        if net_config["DAN2"]:
            features2 = fc7(features)
            outputs = classifier_layer(fc7_relu(features2))
        else:
            outputs = classifier_layer(features)

        classifier_loss = class_criterion(
            outputs.narrow(0, 0, int((inputs.size(0) / 2))), labels_source)

        ## switch between different transfer loss
        if loss_config["name"] == "DAN":
            transfer_loss = transfer_criterion(
                features.narrow(0, 0, int(features.size(0) / 2)),
                features.narrow(0, int(features.size(0) / 2),
                                int(features.size(0) / 2)),
                **loss_config["params"])
        elif loss_config["name"] == "RTN":
            ## RTN is still under developing
            transfer_loss = 0
        elif loss_config["name"] == "JAN":
            softmax_out = softmax_layer(outputs)
            transfer_loss = transfer_criterion([
                features.narrow(0, 0, int(features.size(0) / 2)),
                softmax_out.narrow(0, 0, int(softmax_out.size(0) / 2))
            ], [
                features.narrow(0, int(features.size(0) / 2),
                                int(features.size(0) / 2)),
                softmax_out.narrow(0, int(softmax_out.size(0) / 2),
                                   int(softmax_out.size(0) / 2))
            ], **loss_config["params"])

        if net_config["DAN2"]:
            transfer_loss2 = transfer_criterion(
                features2.narrow(0, 0, int(features2.size(0) / 2)),
                features2.narrow(0, int(features2.size(0) / 2),
                                 int(features2.size(0) / 2)),
                **loss_config["params"])

        total_loss = loss_config["trade_off"] * transfer_loss + classifier_loss
        if net_config["DAN2"]:
            total_loss = total_loss + loss_config["trade_off"] * transfer_loss2
        total_loss.backward()
        optimizer.step()

        ## show loss every show_interval

        if (i + 1) % config["show_interval"] == 0 and not (
                i + 1) % config["test_interval"] == 0:
            print(datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S'),
                  "----------------------------------iter=", i + 1,
                  "\nclassifier_loss=", round(float(classifier_loss),
                                              3), " | transfer_loss=",
                  round(float(transfer_loss), 3))

        ## test in the train
        if (i + 1) % config["test_interval"] == 0:
            print(datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S'),
                  "----------------------------------iter=", i + 1,
                  "\nclassifier_loss=", round(float(classifier_loss),
                                              3), " | transfer_loss=",
                  round(float(transfer_loss), 3))
            print("optimizer_param=", optimizer.param_groups)
            base_network.train(False)
            classifier_layer.train(False)
            if net_config["use_bottleneck"]:
                bottleneck_layer.train(False)
                print(
                    "accuracy=",
                    round(
                        image_classification_test(
                            dset_loaders["target"],
                            nn.Sequential(base_network, bottleneck_layer,
                                          classifier_layer),
                            test_10crop=prep_dict["target"]["test_10crop"],
                            gpu=use_gpu), 3))

            else:
                if net_config["DAN2"]:
                    print(
                        "Domain S[" + args.source + "] accuracy=",
                        round(
                            image_classification_test(
                                dset_loaders["source"],
                                nn.Sequential(base_network, fc7, fc7_relu,
                                              classifier_layer),
                                test_10crop=prep_dict["source"]["test_10crop"],
                                gpu=use_gpu), 3))
                    print(
                        "Domain T[" + args.target + "] accuracy=",
                        round(
                            image_classification_test(
                                dset_loaders["target"],
                                nn.Sequential(base_network, fc7, fc7_relu,
                                              classifier_layer),
                                test_10crop=prep_dict["target"]["test_10crop"],
                                gpu=use_gpu), 3))
                else:
                    print(
                        "accuracy=",
                        round(
                            image_classification_test(
                                dset_loaders["target"],
                                nn.Sequential(base_network, classifier_layer),
                                test_10crop=prep_dict["target"]["test_10crop"],
                                gpu=use_gpu), 3))

        loss_test = nn.BCELoss()

        ## Quyan::snap-------------------------------------------------------------------------------------------------------------------------------------------
        if config["snap"]["snap"] and (i + 1) % config["snap"]["step"] == 0:
            # save model
            torch.save(
                base_network, "../model/office/" + config["loss"]["name"] +
                "_" + config["network"]["name"] + "_iter" +
                str(config["num_iterations"]) + ".pkl")
            # torch.save(bottleneck_layer, "../model/office/" + config["loss"]["name"] + "_" + config["network"]["name"] + "_bottleneck_iter" + str(config["num_iterations"]) + ".pkl")
            torch.save(
                classifier_layer, "../model/office/" + config["loss"]["name"] +
                "_" + config["network"]["name"] + "_classifier_iter" +
                str(config["num_iterations"]) + ".pkl")
コード例 #22
0
def train(config):
    # set pre-process
    prep_config = config["prep"]
    prep_dict = {}
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    # prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = datasets.ImageFolder(data_config['source']['list_path'], transform=prep_dict["source"])
    dset_loaders['source'] = getdataloader(dsets['source'], batchsize=train_bs, num_workers=4, drop_last=True, weightsampler=True)
    dsets["target"] = datasets.ImageFolder(data_config['target']['list_path'], transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs,
                                        shuffle=True, num_workers=4, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [datasets.ImageFolder(data_config['test']['list_path'],
                                                  transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs,
                                               shuffle=False, num_workers=4) for dset in dsets['test']]
    else:
        dsets["test"] = datasets.ImageFolder(data_config['test']['list_path'],
                                             transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs,
                                          shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    # set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.cuda()

    # set test_ad_net
    test_ad_net = network.AdversarialNetwork(base_network.output_num(), 1024, test_ad_net=True)
    test_ad_net = test_ad_net.cuda()

    # add additional network for some methods
    if config['method'] == 'DANN':
        random_layer = None
        ad_net = network.AdversarialNetwork(base_network.output_num(), 1024)
    elif config['method'] == 'MADA':
        random_layer = None
        ad_net = network.AdversarialNetworkClassGroup(base_network.output_num(), 1024, class_num)
    elif config['method'] == 'proposed':
        if config['loss']['random']:
            random_layer = network.RandomLayer([base_network.output_num(), class_num], config['loss']['random_dim'])
            ad_net = network.AdversarialNetwork(config['loss']['random_dim'], 1024)
            ad_net_group = network.AdversarialNetworkGroup(config['loss']['random_dim'], 256, class_num, config['center_threshold'])
        else:
            random_layer = None
            ad_net = network.AdversarialNetwork(base_network.output_num(), 1024)
            ad_net_group = network.AdversarialNetworkGroup(base_network.output_num(), 1024, class_num, config['center_threshold'])
    elif config['method'] == 'base':
        pass
    else:
        if config["loss"]["random"]:
            random_layer = network.RandomLayer([base_network.output_num(), class_num], config["loss"]["random_dim"])
            ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
        else:
            random_layer = None
            ad_net = network.AdversarialNetwork(base_network.output_num() * class_num, 1024)
    if config["loss"]["random"] and config['method'] != 'base' and config['method'] != 'DANN' and config['method'] != 'MADA':
        random_layer.cuda()
    if config['method'] != 'base':
        ad_net = ad_net.cuda()
    if config['method'] == 'proposed':
        ad_net_group = ad_net_group.cuda()

    # set parameters
    if config['method'] == 'proposed':
        parameter_list = base_network.get_parameters() + test_ad_net.get_parameters() + ad_net.get_parameters() + ad_net_group.get_parameters()
    elif config['method'] == 'base':
        parameter_list = base_network.get_parameters() + test_ad_net.get_parameters()
    elif config['method'] == 'MADA':
        parameter_list = base_network.get_parameters() + test_ad_net.get_parameters() + ad_net.get_parameters()
    else:
        parameter_list = base_network.get_parameters() + test_ad_net.get_parameters() + ad_net.get_parameters()

    # set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    # parallel
    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        base_network = nn.DataParallel(base_network)
        test_ad_net = nn.DataParallel(test_ad_net)
        if config['method'] == 'DANN':
            ad_net = nn.DataParallel(ad_net)
        elif config['method'] == 'proposed':
            if config['loss']['random']:
                random_layer = nn.DataParallel(random_layer)
                ad_net = nn.DataParallel(ad_net)
                #将ad_net_group设置成并行将会引发error,原因可能是由于ad_net_group的输出不是tensor类型,parallel还不能支持。
                #ad_net_group = nn.DataParallel(ad_net_group)
            else:
                ad_net = nn.DataParallel(ad_net)
                #ad_net_group = nn.DataParallel(ad_net_group)
        elif config['method'] == 'base':
            pass
        else:
            # CDAN+E
            if config["loss"]["random"]:
                random_layer = nn.DataParallel(random_layer)
                ad_net = nn.DataParallel(ad_net)
            # CDAN
            else:
                ad_net = nn.DataParallel(ad_net)

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == config["test_interval"] - 1:
            base_network.train(False)  # eval() == train(False) is True
            temp_acc = image_classification_test(dset_loaders, base_network, test_10crop=prep_config["test_10crop"])
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()
            print(log_str)
        # if i % config["snapshot_interval"] == 0:
        #     torch.save(nn.Sequential(base_network), osp.join(config["output_path"],
        #                                                      "iter_{:05d}_model.pth.tar".format(i)))

        loss_params = config["loss"]
        # train one iter
        base_network.train(True)
        if config['method'] != 'base':
            ad_net.train(True)
        if config['method'] == 'proposed':
            ad_net_group.train(True)
        # lr_scheduler
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)
        if config['tsne']:
            # feature visualization by using T-SNE
            if i == int(0.98*config['num_iterations']):
                features_source_total = features_source.cpu().detach().numpy()
                features_target_total = features_target.cpu().detach().numpy()
            elif i > int(0.98*config['num_iterations']) and i < int(0.98*config['num_iterations'])+10:
                features_source_total = np.concatenate((features_source_total, features_source.cpu().detach().numpy()))
                features_target_total = np.concatenate((features_target_total, features_target.cpu().detach().numpy()))
            elif i == int(0.98*config['num_iterations'])+10:
                for index in range(config['tsne_num']):
                    features_embeded = TSNE(perplexity=10,n_iter=5000).fit_transform(np.concatenate((features_source_total, features_target_total)))
                    fig = plt.figure()
                    plt.scatter(features_embeded[:len(features_embeded)//2, 0], features_embeded[:len(features_embeded)//2, 1], c='r', s=1)
                    plt.scatter(features_embeded[len(features_embeded)//2:, 0], features_embeded[len(features_embeded)//2:, 1], c='b', s=1)
                    plt.savefig(osp.join(config["output_path"], config['method']+'-'+str(index)+'.png'))
                    plt.close()
            else:
                pass

        assert features_source.size(0) == features_target.size(0), 'The batchsize must be same'
        assert outputs_source.size(0) == outputs_target.size(0), 'The batchsize must be same'
        # source first, target second
        features = torch.cat((features_source, features_target), dim=0)
        outputs = torch.cat((outputs_source, outputs_target), dim=0)

        # output the A_distance
        if i % config["test_interval"] == config["test_interval"] - 1:
            A_distance = cal_A_distance(test_ad_net, features)
            config['A_distance_file'].write(str(A_distance)+'\n')
            config['A_distance_file'].flush()

        softmax_out = nn.Softmax(dim=1)(outputs)
        if config['method'] == 'CDAN+E':
            entropy = loss.Entropy(softmax_out)
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, entropy, network.calc_coeff(i), random_layer)
        elif config['method'] == 'CDAN':
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, None, None, random_layer)
        elif config['method'] == 'DANN':
            transfer_loss = loss.DANN(features, ad_net)
        elif config['method'] == 'MADA':
            transfer_loss = loss.MADA(features, softmax_out, ad_net)
        elif config['method'] == 'proposed':
            entropy = loss.Entropy(softmax_out)
            transfer_loss = loss.proposed([features, outputs], labels_source, ad_net, ad_net_group, entropy,
                                          network.calc_coeff(i), i, random_layer, config['loss']['trade_off23'])
        elif config['method'] == 'base':
            pass
        else:
            raise ValueError('Method cannot be recognized.')
        test_domain_loss = loss.DANN(features.clone().detach(), test_ad_net)
        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
        if config['method'] == 'base':
            total_loss = classifier_loss + test_domain_loss
        else:
            total_loss = loss_params["trade_off"] * transfer_loss + classifier_loss + test_domain_loss
        total_loss.backward()
        optimizer.step()
    # torch.save(best_model, osp.join(config["output_path"], "best_model.pth.tar"))
    return best_acc
コード例 #23
0
ファイル: eval.py プロジェクト: zeta1999/DAPN
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    print(config, data_config)
    #     dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
    #                                 transform=prep_dict["source"])
    #     dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
    #             shuffle=True, num_workers=4, drop_last=True)
    #     dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
    #                                 transform=prep_dict["target"])
    #     dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
    #             shuffle=True, num_workers=4, drop_last=True)

    #     if prep_config["test_10crop"]:
    #         for i in range(10):
    #             dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
    #                                 transform=prep_dict["test"][i]) for i in range(10)]
    #             dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
    #                                 shuffle=False, num_workers=4) for dset in dsets['test']]
    #     else:


    dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                            transform=prep_dict["test"])
    dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                            shuffle=False, num_workers=4)

    print('load data finished')
    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    #base_network = net_config["name"](**net_config["params"])
    #base_network = base_network.cuda()
    #print(base_network)

    base_network = torch.load('snapshot/iter_90000_model.pth.tar')
    base_network = list(base_network.children())[0]
    base_network = base_network.module
    #     for key, value in base_network.state_dict().items():
    #         print(key)
    base_network = list(base_network.children())[9].cuda()
    # base_network= torch.nn.Sequential(*list(base_network.children())[:-1]).cuda()
    base_network = nn.DataParallel(base_network)
    print(base_network)
    #base_network.load_state_dict(checkpoint, strict=False)
    #     ## add additional network for some methods
    #     if config["loss"]["random"]:
    #         random_layer = network.RandomLayer([base_network.output_num(), class_num], config["loss"]["random_dim"])
    #         ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
    #     else:
    #         random_layer = None
    #         ad_net = network.AdversarialNetwork(base_network.output_num() * class_num, 1024)
    #     if config["loss"]["random"]:
    #         random_layer.cuda()
    #     ad_net = ad_net.cuda()
    #     parameter_list = base_network.get_parameters()# + ad_net.get_parameters()

    #     ## set optimizer
    #     optimizer_config = config["optimizer"]
    #     optimizer = optimizer_config["type"](parameter_list, \
    #                     **(optimizer_config["optim_params"]))
    #     param_lr = []
    #     for param_group in optimizer.param_groups:
    #         param_lr.append(param_group["lr"])
    #     schedule_param = optimizer_config["lr_param"]
    #     lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    #     gpus = config['gpu'].split(',')
    #     if len(gpus) > 1:
    # #         ad_net = nn.DataParallel(ad_net, device_ids=[int(i) for i in gpus])
    #         base_network = nn.DataParallel(base_network, device_ids=[int(i) for i in gpus])

    ## train
    #     len_train_source = len(dset_loaders["source"])
    #     len_train_target = len(dset_loaders["target"])
    #     transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    #     best_acc = 0.0

    base_network.train(False)
    image_classification_test(dset_loaders, \
        base_network, test_10crop=prep_config["test_10crop"])

    return
コード例 #24
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
                                        shuffle=True, num_workers=0, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                       transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                               shuffle=False, num_workers=0) for dset in dsets['test']]
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                          shuffle=False, num_workers=0)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    # base_network = base_network.cuda()

    ## 添加判别器D_s,D_t,生成器G_s2t,G_t2s

    z_dimension = 256
    D_s = network.models["Discriminator"]()
    # D_s = D_s.cuda()
    G_s2t = network.models["Generator"](z_dimension, 1024)
    # G_s2t = G_s2t.cuda()

    D_t = network.models["Discriminator"]()
    # D_t = D_t.cuda()
    G_t2s = network.models["Generator"](z_dimension, 1024)
    # G_t2s = G_t2s.cuda()

    criterion_GAN = torch.nn.MSELoss()
    criterion_cycle = torch.nn.L1Loss()
    criterion_identity = torch.nn.L1Loss()
    criterion_Sem = torch.nn.L1Loss()

    optimizer_G = torch.optim.Adam(itertools.chain(G_s2t.parameters(), G_t2s.parameters()), lr=0.0003)
    optimizer_D_s = torch.optim.Adam(D_s.parameters(), lr=0.0003)
    optimizer_D_t = torch.optim.Adam(D_t.parameters(), lr=0.0003)

    fake_S_buffer = ReplayBuffer()
    fake_T_buffer = ReplayBuffer()

    classifier_optimizer = torch.optim.Adam(base_network.parameters(), lr=0.0003)
    ## 添加分类器
    classifier1 = net.Net(256,class_num)
    # classifier1 = classifier1.cuda()
    classifier1_optim = optim.Adam(classifier1.parameters(), lr=0.0003)

    ## add additional network for some methods
    if config["loss"]["random"]:
        random_layer = network.RandomLayer([base_network.output_num(), class_num], config["loss"]["random_dim"])
        ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
    else:
        random_layer = None
        ad_net = network.AdversarialNetwork(base_network.output_num() * class_num, 1024)
    if config["loss"]["random"]:
        random_layer.cuda()
    # ad_net = ad_net.cuda()
    parameter_list = base_network.get_parameters() + ad_net.get_parameters()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                                         **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        ad_net = nn.DataParallel(ad_net, device_ids=[int(i) for i in gpus])
        base_network = nn.DataParallel(base_network, device_ids=[int(i) for i in gpus])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == config["test_interval"] - 1:
            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders, \
                                                 base_network, test_10crop=prep_config["test_10crop"])
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model

                now = datetime.datetime.now()
                d = str(now.month) + '-' + str(now.day) + ' ' + str(now.hour) + ':' + str(now.minute) + ":" + str(
                    now.second)
                torch.save(best_model, osp.join(config["output_path"],
                                                "{}_to_{}_best_model_acc-{}_{}.pth.tar".format(args.source, args.target,
                                                                                               best_acc, d)))
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()

            print(log_str)
        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                                                             "{}_to_{}_iter_{:05d}_model_{}.pth.tar".format(args.source,
                                                                                                            args.target,
                                                                                                            i, str(
                                                                     datetime.datetime.utcnow()))))
        print("it_train: {:05d} / {:05d} start".format(i, config["num_iterations"]))
        loss_params = config["loss"]
        ## train one iter
        classifier1.train(True)
        base_network.train(True)
        ad_net.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()


        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        # inputs_source, inputs_target, labels_source = inputs_source.cuda(), inputs_target.cuda(), labels_source.cuda()

        # 提取特征
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)
        features = torch.cat((features_source, features_target), dim=0)
        outputs = torch.cat((outputs_source, outputs_target), dim=0)
        softmax_out = nn.Softmax(dim=1)(outputs)

        outputs_source1 = classifier1(features_source.detach())
        outputs_target1 = classifier1(features_target.detach())
        outputs1 = torch.cat((outputs_source1,outputs_target1),dim=0)
        softmax_out1 = nn.Softmax(dim=1)(outputs1)

        softmax_out = (1-args.cla_plus_weight)*softmax_out + args.cla_plus_weight*softmax_out1

        if config['method'] == 'CDAN+E':
            entropy = loss.Entropy(softmax_out)
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, entropy, network.calc_coeff(i), random_layer)
        elif config['method'] == 'CDAN':
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, None, None, random_layer)
        elif config['method'] == 'DANN':
            transfer_loss = loss.DANN(features, ad_net)
        else:
            raise ValueError('Method cannot be recognized.')
        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)

        # Cycle
        num_feature = features_source.size(0)
        # =================train discriminator T
        real_label = Variable(torch.ones(num_feature))
        # real_label = Variable(torch.ones(num_feature)).cuda()
        fake_label = Variable(torch.zeros(num_feature))
        # fake_label = Variable(torch.zeros(num_feature)).cuda()

        # 训练生成器
        optimizer_G.zero_grad()

        # Identity loss
        same_t = G_s2t(features_target.detach())
        loss_identity_t = criterion_identity(same_t, features_target)

        same_s = G_t2s(features_source.detach())
        loss_identity_s = criterion_identity(same_s, features_source)

        # Gan loss
        fake_t = G_s2t(features_source.detach())
        pred_fake = D_t(fake_t)
        loss_G_s2t = criterion_GAN(pred_fake, labels_source.float())

        fake_s = G_t2s(features_target.detach())
        pred_fake = D_s(fake_s)
        loss_G_t2s = criterion_GAN(pred_fake, labels_source.float())

        # cycle loss
        recovered_s = G_t2s(fake_t)
        loss_cycle_sts = criterion_cycle(recovered_s, features_source)

        recovered_t = G_s2t(fake_s)
        loss_cycle_tst = criterion_cycle(recovered_t, features_target)

        # sem loss
        pred_recovered_s = base_network.fc(recovered_s)
        pred_fake_t = base_network.fc(fake_t)
        loss_sem_t2s = criterion_Sem(pred_recovered_s, pred_fake_t)

        pred_recovered_t = base_network.fc(recovered_t)
        pred_fake_s = base_network.fc(fake_s)
        loss_sem_s2t = criterion_Sem(pred_recovered_t, pred_fake_s)

        loss_cycle = loss_cycle_tst + loss_cycle_sts
        weights = args.weight_in_lossG.split(',')
        loss_G = float(weights[0]) * (loss_identity_s + loss_identity_t) + \
                 float(weights[1]) * (loss_G_s2t + loss_G_t2s) + \
                 float(weights[2]) * loss_cycle + \
                 float(weights[3]) * (loss_sem_s2t + loss_sem_t2s)



        # 训练softmax分类器
        outputs_fake = classifier1(fake_t.detach())
        # 分类器优化
        classifier_loss1 = nn.CrossEntropyLoss()(outputs_fake, labels_source)
        classifier1_optim.zero_grad()
        classifier_loss1.backward()
        classifier1_optim.step()

        total_loss = loss_params["trade_off"] * transfer_loss + classifier_loss + args.cyc_loss_weight*loss_G
        total_loss.backward()
        optimizer.step()
        optimizer_G.step()

        ###### Discriminator S ######
        optimizer_D_s.zero_grad()

        # Real loss
        pred_real = D_s(features_source.detach())
        loss_D_real = criterion_GAN(pred_real, real_label)

        # Fake loss
        fake_s = fake_S_buffer.push_and_pop(fake_s)
        pred_fake = D_s(fake_s.detach())
        loss_D_fake = criterion_GAN(pred_fake, fake_label)

        # Total loss
        loss_D_s = loss_D_real + loss_D_fake
        loss_D_s.backward()

        optimizer_D_s.step()
        ###################################

        ###### Discriminator t ######
        optimizer_D_t.zero_grad()

        # Real loss
        pred_real = D_t(features_target.detach())
        loss_D_real = criterion_GAN(pred_real, real_label)

        # Fake loss
        fake_t = fake_T_buffer.push_and_pop(fake_t)
        pred_fake = D_t(fake_t.detach())
        loss_D_fake = criterion_GAN(pred_fake, fake_label)

        # Total loss
        loss_D_t = loss_D_real + loss_D_fake
        loss_D_t.backward()
        optimizer_D_t.step()
        print("it_train: {:05d} / {:05d} over".format(i, config["num_iterations"]))
    now = datetime.datetime.now()
    d = str(now.month)+'-'+str(now.day)+' '+str(now.hour)+':'+str(now.minute)+":"+str(now.second)
    torch.save(best_model, osp.join(config["output_path"],
                                    "{}_to_{}_best_model_acc-{}_{}.pth.tar".format(args.source, args.target,
                                                                            best_acc,d)))
    return best_acc
コード例 #25
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    tensor_writer = SummaryWriter(config["output_path"])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    # dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
    #                             transform=prep_dict["source"])
    # dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
    #         shuffle=True, num_workers=4, drop_last=True)
    # dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
    #                             transform=prep_dict["target"])
    # dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
    #         shuffle=True, num_workers=4, drop_last=True)

    dsets["source"] = ImageFolder(root=data_config["source"]["list_path"], \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)
    dsets["target"] = ImageFolder(root=data_config["target"]["list_path"], \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["val"] = [ImageFolder(root=data_config["source"]["list_path"], \
                                transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["val"] = [DataLoader(dset, batch_size=test_bs, \
                                shuffle=False, num_workers=4) for dset in dsets['val']]

            dsets["test"] = [ImageFolder(root=data_config["target"]["list_path"], \
                                transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                shuffle=False, num_workers=4) for dset in dsets['test']]
    else:
        dsets["test"] = ImageFolder(root=data_config["target"]["list_path"], \
                                transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = torch.load(
        "./snapshot/finetune_pet/iter_01000_model.pth.tar")[0]
    base_network = base_network.cuda()
    classifier_network = network.Classifier(
        class_num=config["network"]["params"]["class_num"])
    classifier_network = classifier_network.cuda()

    parameter_list = classifier_network.get_parameters()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        base_network = nn.DataParallel(base_network,
                                       device_ids=[int(i) for i in gpus])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        print(i)
        if i % config["test_interval"] == config["test_interval"] - 1:
            base_network.train(False)

            temp_acc, output, label, feature, logit = image_classification_val(dset_loaders, \
                base_network, classifier_network, test_10crop=prep_config["test_10crop"])
            np.save(
                os.path.join(config["output_path"],
                             str(i) + '_output_src.npy'), output)
            np.save(
                os.path.join(config["output_path"],
                             str(i) + '_label_src.npy'), label)
            np.save(
                os.path.join(config["output_path"],
                             str(i) + '_feature_src.npy'), feature)
            np.save(
                os.path.join(config["output_path"],
                             str(i) + '_logit_src.npy'), logit)

            temp_acc, output, label, feature, logit = image_classification_test(dset_loaders, \
                base_network, classifier_network, test_10crop=prep_config["test_10crop"])
            np.save(
                os.path.join(config["output_path"],
                             str(i) + '_output.npy'), output)
            np.save(os.path.join(config["output_path"],
                                 str(i) + '_label.npy'), label)
            np.save(
                os.path.join(config["output_path"],
                             str(i) + '_feature.npy'), feature)
            np.save(os.path.join(config["output_path"],
                                 str(i) + '_logit.npy'), logit)

            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str + "\n")
            config["out_file"].flush()
            print(log_str)
        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(classifier_network), osp.join(config["output_path"], \
                "iter_{:05d}_classifier.pth.tar".format(i)))

        loss_params = config["loss"]
        ## train one iter
        base_network.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(
        ), inputs_target.cuda(), labels_source.cuda()
        features_source, _ = base_network(inputs_source)
        embed_source, outputs_source = classifier_network(features_source)
        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
        total_loss = classifier_loss
        total_loss.backward()
        optimizer.step()
    torch.save(best_model, osp.join(config["output_path"],
                                    "best_model.pth.tar"))
    return best_acc
コード例 #26
0
ファイル: train_dcan.py プロジェクト: hello-trouble/GDCAN
def train(config):
    # pre-process training and test data
    prep_dict = {
        'source': prep.image_train(**config['prep']['params']),
        'target': prep.image_train(**config['prep']['params'])
    }
    if config['prep']['test_10crop']:
        prep_dict['test'] = prep.image_test_10crop(**config['prep']['params'])
    else:
        prep_dict['test'] = prep.image_test(**config['prep']['params'])

    data_set = {}
    dset_loaders = {}
    data_config = config['data']
    data_set['source'] = ImageList(open(
        data_config['source']['list_path']).readlines(),
                                   transform=prep_dict['source'])
    dset_loaders['source'] = torch.utils.data.DataLoader(
        data_set['source'],
        batch_size=data_config['source']['batch_size'],
        shuffle=True,
        num_workers=4,
        drop_last=True)
    data_set['target'] = ImageList(open(
        data_config['target']['list_path']).readlines(),
                                   transform=prep_dict['target'])
    dset_loaders['target'] = torch.utils.data.DataLoader(
        data_set['target'],
        batch_size=data_config['target']['batch_size'],
        shuffle=True,
        num_workers=4,
        drop_last=True)
    if config['prep']['test_10crop']:
        data_set['test'] = [
            ImageList(open(data_config['test']['list_path']).readlines(),
                      transform=prep_dict['test'][i]) for i in range(10)
        ]
        dset_loaders['test'] = [
            torch.utils.data.DataLoader(
                dset,
                batch_size=data_config['test']['batch_size'],
                shuffle=False,
                num_workers=4) for dset in data_set['test']
        ]
    else:
        data_set['test'] = ImageList(open(
            data_config['test']['list_path']).readlines(),
                                     transform=prep_dict['test'])
        dset_loaders['test'] = torch.utils.data.DataLoader(
            data_set['test'],
            batch_size=data_config['test']['batch_size'],
            shuffle=False,
            num_workers=4)

    # set base network, classifier network, residual net
    class_num = config['network']['params']['class_num']
    net_config = config['network']
    if net_config['name'] == '50':
        base_network = dcca_resnet50()
    elif net_config['name'] == '101':
        base_network = dcca_resnet101()
    else:
        raise ValueError('base network %s not found!' % (net_config['name']))

    classifier_layer = nn.Linear(2048, class_num)
    # feature residual layer: two fully connected layers
    residual_fc1 = nn.Linear(2048, 2048)
    residual_bn1 = nn.BatchNorm1d(2048)
    residual_fc2 = nn.Linear(2048, 128)
    residual_bn2 = nn.BatchNorm1d(128)
    residual_fc3 = nn.Linear(128, 2048)
    classifier_layer.weight.data.normal_(0, 0.01)
    classifier_layer.bias.data.fill_(0.0)
    residual_fc1.weight.data.normal_(0, 0.005)
    residual_fc1.bias.data.fill_(0.1)
    residual_fc2.weight.data.normal_(0, 0.005)
    residual_fc2.bias.data.fill_(0.1)
    residual_fc3.weight.data.normal_(0, 0.005)
    residual_fc3.bias.data.fill_(0.1)
    feature_residual_layer = nn.Sequential(residual_fc2, nn.ReLU(),
                                           residual_fc3)

    # class residual layer: two fully connected layers
    residual_fc22 = nn.Linear(classifier_layer.out_features,
                              classifier_layer.out_features)
    residual_bn22 = nn.BatchNorm1d(classifier_layer.out_features)
    residual_fc23 = nn.Linear(classifier_layer.out_features,
                              classifier_layer.out_features)
    residual_fc22.weight.data.normal_(0, 0.005)
    residual_fc22.bias.data.fill_(0.1)
    residual_fc23.weight.data.normal_(0, 0.005)
    residual_fc23.bias.data.fill_(0.1)
    class_residual_layer = nn.Sequential(residual_fc22, nn.ReLU(),
                                         residual_fc23)

    base_network = base_network.cuda()
    feature_residual_layer = feature_residual_layer.cuda()
    classifier_layer = classifier_layer.cuda()
    class_residual_layer = class_residual_layer.cuda()
    softmax_layer = nn.Softmax().cuda()

    # set optimizer
    parameter_list = [{
        'params': base_network.parameters(),
        'lr_mult': 1,
        'decay_mult': 2
    }, {
        'params': classifier_layer.parameters(),
        'lr_mult': 10,
        'decay_mult': 2
    }, {
        'params': feature_residual_layer.parameters(),
        'lr_mult': 0.01,
        'decay_mult': 2
    }, {
        'params': class_residual_layer.parameters(),
        'lr_mult': 0.01,
        'decay_mult': 2
    }]
    optimizer_config = config['optimizer']
    optimizer = optimizer_config['type'](parameter_list,
                                         **(optimizer_config['optim_params']))
    schedule_param = optimizer_config['lr_param']
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config['lr_type']]

    # set loss
    class_criterion = nn.CrossEntropyLoss().cuda()
    loss_config = config['loss']
    if 'params' not in loss_config:
        loss_config['params'] = {}

    # train
    len_train_source = len(dset_loaders['source'])
    len_train_target = len(dset_loaders['target'])
    best_acc = 0.0
    since = time.time()
    for num_iter in tqdm(range(config['max_iter'])):
        if num_iter % config['val_iter'] == 0 and num_iter != 0:
            base_network.train(False)
            classifier_layer.train(False)
            feature_residual_layer.train(False)
            class_residual_layer.train(False)
            base_network = nn.Sequential(base_network)
            classifier_layer = nn.Sequential(classifier_layer)
            feature_residual_layer = nn.Sequential(feature_residual_layer)
            class_residual_layer = nn.Sequential(class_residual_layer)
            temp_acc = image_classification_test(
                loader=dset_loaders,
                base_net=base_network,
                classifier_layer=classifier_layer,
                residual_layer1=feature_residual_layer,
                residual_layer2=class_residual_layer,
                test_10crop=config['prep']['test_10crop'],
                config=config,
                num_iter=num_iter)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = {
                    'base': base_network.state_dict(),
                    'classifier': classifier_layer.state_dict(),
                    'feature_residual': feature_residual_layer.state_dict(),
                    'class_residual': class_residual_layer.state_dict()
                }

            log_str = 'iter: {:d}, all_accu: {:.4f},\ttime: {:.4f}'.format(
                num_iter, temp_acc,
                time.time() - since)
            config['logger'].logger.debug(log_str)
            config['results'][num_iter].append(temp_acc)

        # This has any effect only on modules such as Dropout or BatchNorm.
        base_network.train(True)
        classifier_layer.train(True)
        feature_residual_layer.train(True)
        class_residual_layer.train(True)

        # freeze BN layers
        for m in base_network.modules():
            if isinstance(m, nn.BatchNorm2d):
                m.training = False
                m.weight.requires_grad = False
                m.bias.requires_grad = False

        # load data
        if num_iter % len_train_source == 0:
            iter_source = iter(dset_loaders['source'])
        if num_iter % len_train_target == 0:
            iter_target = iter(dset_loaders['target'])
        inputs_source, labels_source = iter_source.next()
        inputs_target, _ = iter_target.next()
        batch_size = len(labels_source)
        inputs_source, inputs_target, labels_source = inputs_source.cuda(
        ), inputs_target.cuda(), labels_source.cuda()

        optimizer = lr_scheduler(optimizer, num_iter / config['max_iter'],
                                 **schedule_param)
        optimizer.zero_grad()

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features_base = base_network(inputs)
        features_residual = feature_residual_layer(features_base)
        total_feature_residual = features_base + features_residual

        # source classification loss with original features
        output_base = classifier_layer(features_base)
        classifier_loss = class_criterion(output_base[:batch_size, :],
                                          labels_source)

        # target residual feature entropy loss
        residual_output_base = classifier_layer(total_feature_residual)
        output_residual = class_residual_layer(residual_output_base)
        total_output_residual = residual_output_base + output_residual
        softmax_output_base = softmax_layer(output_base)
        total_softmax_residual = softmax_layer(total_output_residual)
        entropy_loss = EntropyLoss(total_softmax_residual[batch_size:, :])

        # alignment of L task-specific feature layers (Here, we have one layer)
        transfer_loss = MMD(features_base[:batch_size, :],
                            total_feature_residual[batch_size:, :])
        # alignment of softmax layer
        transfer_loss += MMD(softmax_output_base[:batch_size, :],
                             total_softmax_residual[batch_size:, :],
                             kernel_num=1,
                             fix_sigma=1.68)

        source_labels_data = labels_source.data.float()
        sum_reg_loss = 0
        for k in range(class_num):
            source_k_index = []
            for index, source_k in enumerate(source_labels_data):
                # find all indexes of k-th class source samples
                if source_k == k:
                    source_k_index.append(index)
            fea_reg_loss = 0
            out_reg_loss = 0
            if len(source_k_index) > 0:
                # random subset indexes of source samples
                source_rand_index = []
                index = 0
                for z in range(batch_size):
                    prob = random.random()
                    if prob < config['random_prob'] / class_num:
                        source_rand_index.append(index)
                        index += 1

                if len(source_rand_index) > 0:
                    # source feature of k-th class
                    source_k_fea = features_base.index_select(
                        0,
                        torch.tensor(source_k_index, dtype=torch.long).cuda())
                    source_k_out = output_base.index_select(
                        0,
                        torch.tensor(source_k_index, dtype=torch.long).cuda())

                    # random selected source feature
                    source_rand_fea = total_feature_residual.index_select(
                        0,
                        torch.tensor(source_rand_index,
                                     dtype=torch.long).cuda())
                    source_rand_out = total_output_residual.index_select(
                        0,
                        torch.tensor(source_rand_index,
                                     dtype=torch.long).cuda())

                    fea_reg_loss = MMD_reg(source_k_fea, source_rand_fea)
                    out_reg_loss = MMD_reg(source_k_out,
                                           source_rand_out,
                                           kernel_num=1,
                                           fix_sigma=1.68)

            sum_reg_loss += (fea_reg_loss + out_reg_loss)

        total_loss = classifier_loss + \
                     config['loss']['alpha_off'] * (transfer_loss +
                                                    config['loss']['constant_off'] * sum_reg_loss) + \
                     config['loss']['beta_off'] * entropy_loss
        total_loss.backward()
        optimizer.step()

        if num_iter % config['val_iter'] == 0:
            config['logger'].logger.debug(
                'class: {:.4f}\tmmd: {:.4f}\tmmd_seg: {:.4f}\tentropy: {:.4f}'.
                format(classifier_loss.item(), transfer_loss.item(),
                       config['loss']['constant_off'] * sum_reg_loss,
                       entropy_loss.item() * config['loss']['beta_off']))
            if config['is_writer']:
                config['writer'].add_scalars(
                    'train', {
                        'class':
                        classifier_loss.item(),
                        'mmd':
                        transfer_loss.item(),
                        'mmd_seg':
                        config['loss']['constant_off'] * sum_reg_loss.item(),
                        'entropy':
                        config['loss']['beta_off'] * entropy_loss.item()
                    }, num_iter)

    if config['is_writer']:
        config['writer'].close()

    torch.save(
        best_model,
        osp.join(config['path']['model'], config['task'] + '_best_model.pth'))
    return best_acc
コード例 #27
0
ファイル: evaluate.py プロジェクト: notfolder/ALDA
def evaluate(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]

    source_list = open(data_config["source"]["list_path"]).readlines()
    target_list = open(data_config["target"]["list_path"]).readlines()

    dsets["source"] = ImageList(source_list, \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)
    dsets["target"] = ImageList(target_list, \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)

    if prep_config["test_10crop"]:
        for i in range(10):
            test_list = [
                '.' + i
                for i in open(data_config["test"]["list_path"]).readlines()
            ]
            dsets["test"] = [ImageList(test_list, \
                                transform=prep_dict["test"][i]) for i in range(10)]
            dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
                                shuffle=False, num_workers=4) for dset in dsets['test']]
    else:
        test_list = [
            '.' + i
            for i in open(data_config["test"]["list_path"]).readlines()
        ]
        dsets["test"] = ImageList(test_list, \
                                transform=prep_dict["test"])
        dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
                                shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.to(network.dev)
    if config["restore_path"]:
        checkpoint = torch.load(
            osp.join(config["restore_path"], "best_model.pth"))
        base_network.load_state_dict(checkpoint)
        print("successfully restore from ",
              osp.join(config["restore_path"], "best_model.pth"))

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        base_network = nn.DataParallel(
            base_network, device_ids=[int(i) for i in range(len(gpus))])

    evaluater = Eval(class_num)

    base_network.train(False)
    temp_acc, predict, all_label = image_classification_test(dset_loaders, \
        base_network, test_10crop=prep_config["test_10crop"])
    print("arg acc:", temp_acc)
    evaluater.add_batch(predict, all_label)
    evaluater.Print_Every_class_Eval()
    evaluater.reset()
    return
コード例 #28
0
def test(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    prep_dict["target"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    else:
        prep_dict["test"] = prep.image_test( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]

    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = util_data.DataLoader(dsets["source"], \
            batch_size=data_config["source"]["batch_size"], \
            shuffle=True, num_workers=2)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = util_data.DataLoader(dsets["target"], \
            batch_size=data_config["target"]["batch_size"], \
            shuffle=True, num_workers=2)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"+str(i)] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["test"+str(i)] = util_data.DataLoader(dsets["test"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=2)

            dsets["target"+str(i)] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["target"+str(i)] = util_data.DataLoader(dsets["target"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=2)
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = util_data.DataLoader(dsets["test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=2)

        dsets["target_test"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["target_test"] = util_data.DataLoader(dsets["target_test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=2)

    class_num = config["network"]["params"]["class_num"]

    # load checkpoint
    print('load model from {}'.format(config['ckpt_path']))
    # load in an old way
    # base_network = torch.load(config["ckpt_path"])[0]
    # recommended practice
    ckpt = torch.load(config['ckpt_path'])
    print('recorded best precision: {:0.4f} at step {}'.format(
        ckpt["precision"], ckpt["step"]))
    train_accuracy = ckpt["precision"]
    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network.load_state_dict(ckpt['base_network'])

    centroids = None
    if 'center_criterion' in ckpt.keys():
        centroids = ckpt['center_criterion']['centers'].cpu()
    target_centroids = None
    if 'target_center_criterion' in ckpt.keys():
        target_centroids = ckpt['target_center_criterion']['centers'].cpu()

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        base_network = base_network.cuda()

    ## test
    print("start test: ")
    base_network.train(False)
    if config["ly_type"] == 'cosine':
        test_acc, test_confusion_matrix = image_classification_test(dset_loaders, \
            base_network, test_10crop=prep_config["test_10crop"], \
            gpu=use_gpu)
    elif config["ly_type"] == "euclidean":
        eval_centroids = None
        if centroids is not None:
            eval_centroids = centroids
        if target_centroids is not None:
            eval_centroids = target_centroids
        test_acc, test_confusion_matrix = utils.distance_classification_test(dset_loaders, \
            base_network, eval_centroids, test_10crop=prep_config["test_10crop"], \
            gpu=use_gpu)

    # save train/test accuracy as pkl file
    with open(os.path.join(config["output_path"], 'accuracy.pkl'),
              'wb') as pkl_file:
        pkl.dump({'train': train_accuracy, 'test': test_acc}, pkl_file)

    ## top k confusion classes for each class
    #base_data_path = os.path.split(data_config["target"]["list_path"])[0]
    #with open(os.path.join(base_data_path, 'label2class.json'), "r") as f:
    #    obj = json.load(f)[0]
    #    label_to_class = {int(k):v for k, v in obj.items()} #convert key to int

    np.set_printoptions(precision=2)
    log_str = "train precision: {:.5f}\ttest precision: {:.5f}\nconfusion matrix:\n{}\n".format(
        train_accuracy, test_acc, test_confusion_matrix)
    config["out_file"].write(log_str)
    config["out_file"].flush()
    print(log_str)

    return test_acc
コード例 #29
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    prep_dict["target"] = prep.image_train( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])
    else:
        prep_dict["test"] = prep.image_test( \
                            resize_size=prep_config["resize_size"], \
                            crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()
    transfer_criterion = loss.PADA
    loss_params = config["loss"]

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]

    # seperate the source and validation set
    cls_source_list, cls_validation_list = sep.split_set(
        data_config["source"]["list_path"],
        config["network"]["params"]["class_num"])
    source_list = sep.dimension_rd(cls_source_list)

    dsets["source"] = ImageList(source_list, \
                                transform=prep_dict["source"])
    dset_loaders["source"] = util_data.DataLoader(dsets["source"], \
            batch_size=data_config["source"]["batch_size"], \
            shuffle=True, num_workers=4)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = util_data.DataLoader(dsets["target"], \
            batch_size=data_config["target"]["batch_size"], \
            shuffle=True, num_workers=4)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test"+str(i)] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["test"+str(i)] = util_data.DataLoader(dsets["test"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

            dsets["target"+str(i)] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["test"]["val"+str(i)])
            dset_loaders["target"+str(i)] = util_data.DataLoader(dsets["target"+str(i)], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["test"] = util_data.DataLoader(dsets["test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

        dsets["target_test"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["test"])
        dset_loaders["target_test"] = MyDataLoader(dsets["target_test"], \
                                batch_size=data_config["test"]["batch_size"], \
                                shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["params"]["new_cls"]:
        if net_config["params"]["use_bottleneck"]:
            parameter_list = [{"params":base_network.feature_layers.parameters(), "lr":1}, \
                            {"params":base_network.bottleneck.parameters(), "lr":10}, \
                            {"params":base_network.fc.parameters(), "lr":10}]
        else:
            parameter_list = [{"params":base_network.feature_layers.parameters(), "lr":1}, \
                            {"params":base_network.fc.parameters(), "lr":10}]
    else:
        parameter_list = [{"params": base_network.parameters(), "lr": 1}]

    ## add additional network for some methods
    class_weight = torch.from_numpy(np.array([1.0] * class_num))
    if use_gpu:
        class_weight = class_weight.cuda()
    ad_net = network.AdversarialNetwork(base_network.output_num())
    gradient_reverse_layer = network.AdversarialLayer(
        high_value=config["high"])
    if use_gpu:
        ad_net = ad_net.cuda()
    parameter_list.append({"params": ad_net.parameters(), "lr": 10})

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]) - 1
    len_train_target = len(dset_loaders["target"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    best_model = 0
    for i in range(config["num_iterations"]):
        if (i + 1) % config["test_interval"] == 0:
            base_network.train(False)
            temp_acc = image_classification_test(dset_loaders, \
                base_network, test_10crop=prep_config["test_10crop"], \
                gpu=use_gpu)
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
            config["out_file"].write(log_str)
            config["out_file"].flush()
            print(log_str)
        if (i + 1) % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                "iter_{:05d}_model.pth.tar".format(i)))

        # if i % loss_params["update_iter"] == loss_params["update_iter"] - 1:
        #     base_network.train(False)
        #     target_fc8_out = image_classification_predict(dset_loaders, base_network, softmax_param=config["softmax_param"])
        #     class_weight = torch.mean(target_fc8_out, 0)
        #     class_weight = (class_weight / torch.mean(class_weight)).cuda().view(-1)
        #     class_criterion = nn.CrossEntropyLoss(weight = class_weight)

        ## train one iter
        base_network.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = \
                Variable(inputs_source).cuda(), Variable(inputs_target).cuda(), \
                Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(inputs_source), \
                Variable(inputs_target), Variable(labels_source)

        inputs = torch.cat((inputs_source, inputs_target), dim=0)
        features, outputs = base_network(inputs)

        # #
        # if i % 100 == 0:
        #     check = dev.get_label_list(open(data_config["source"]["list_path"]).readlines(),
        #                                base_network,
        #                                prep_config["resize_size"],
        #                                prep_config["crop_size"],
        #                                data_config["target"]["batch_size"],
        #                                use_gpu)
        #     f = open("Class_result.txt", "a+")
        #     f.close()
        #     for cls in range(class_num):
        #         count = 0
        #         for j in check:
        #             if int(j.split(" ")[1].replace("\n", "")) == cls:
        #                 count = count + 1
        #         f = open("Source_result.txt", "a+")
        #         f.write("Source_Class: " + str(cls) + "\n" + "Number of images: " + str(count) + "\n")
        #         f.close()
        #
        #     check = dev.get_label_list(open(data_config["target"]["list_path"]).readlines(),
        #                                base_network,
        #                                prep_config["resize_size"],
        #                                prep_config["crop_size"],
        #                                data_config["target"]["batch_size"],
        #                                use_gpu)
        #     f = open("Class_result.txt", "a+")
        #     f.write("Iteration: " + str(i) + "\n")
        #     f.close()
        #     for cls in range(class_num):
        #         count = 0
        #         for j in check:
        #             if int(j.split(" ")[1].replace("\n", "")) == cls:
        #                 count = count + 1
        #         f = open("Class_result.txt", "a+")
        #         f.write("Target_Class: " + str(cls) + "\n" + "Number of images: " + str(count) + "\n")
        #         f.close()

        #
        # #
        # print("Training test:")
        # print(features)
        # print(features.shape)
        # print(outputs)
        # print(outputs.shape)

        softmax_out = nn.Softmax(dim=1)(outputs).detach()
        ad_net.train(True)
        weight_ad = torch.ones(inputs.size(0))
        # label_numpy = labels_source.data.cpu().numpy()
        # for j in range(int(inputs.size(0) / 2)):
        #     weight_ad[j] = class_weight[int(label_numpy[j])]
        # weight_ad = weight_ad / torch.max(weight_ad[0:int(inputs.size(0)/2)])
        # for j in range(int(inputs.size(0) / 2), inputs.size(0)):
        #     weight_ad[j] = 1.0
        transfer_loss = transfer_criterion(features, ad_net, gradient_reverse_layer, \
                                           weight_ad, use_gpu)

        classifier_loss = class_criterion(
            outputs.narrow(0, 0, int(inputs.size(0) / 2)), labels_source)

        total_loss = loss_params["trade_off"] * transfer_loss + classifier_loss
        total_loss.backward()
        optimizer.step()
    cv_loss = dev.cross_validation_loss(
        base_network, base_network, cls_source_list,
        data_config["target"]["list_path"], cls_validation_list, class_num,
        prep_config["resize_size"], prep_config["crop_size"],
        data_config["target"]["batch_size"], use_gpu)
    print(cv_loss)
コード例 #30
0
def train(config):
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train(**config["prep"]['params'])
    prep_dict["target"] = prep.image_train(**config["prep"]['params'])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop(**config["prep"]['params'])
    else:
        prep_dict["test"] = prep.image_test(**config["prep"]['params'])

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    train_bs = data_config["source"]["batch_size"]
    test_bs = data_config["test"]["batch_size"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = DataLoader(dsets["source"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = DataLoader(dsets["target"], batch_size=train_bs, \
            shuffle=True, num_workers=4, drop_last=True)

    #     if prep_config["test_10crop"]:
    #         for i in range(10):
    #             dsets["test"] = [ImageList(open(data_config["test"]["list_path"]).readlines(), \
    #                                 transform=prep_dict["test"][i]) for i in range(10)]
    #             dset_loaders["test"] = [DataLoader(dset, batch_size=test_bs, \
    #                                 shuffle=False, num_workers=4) for dset in dsets['test']]
    #     else:
    #         dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
    #                                 transform=prep_dict["test"])
    #         dset_loaders["test"] = DataLoader(dsets["test"], batch_size=test_bs, \
    #                                 shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])
    base_network = base_network.cuda()

    ## add additional network for some methods
    if config["loss"]["random"]:
        random_layer = network.RandomLayer(
            [base_network.output_num(), class_num],
            config["loss"]["random_dim"])
        ad_net = network.AdversarialNetwork(config["loss"]["random_dim"], 1024)
    else:
        random_layer = None
        ad_net = network.AdversarialNetwork(
            base_network.output_num() * class_num, 1024)
    if config["loss"]["random"]:
        random_layer.cuda()
    ad_net = ad_net.cuda()
    parameter_list = base_network.get_parameters() + ad_net.get_parameters()

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optimizer_config["type"](parameter_list, \
                    **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    gpus = config['gpu'].split(',')
    if len(gpus) > 1:
        ad_net = nn.DataParallel(ad_net, device_ids=[int(i) for i in gpus])
        base_network = nn.DataParallel(base_network,
                                       device_ids=[int(i) for i in gpus])

    ## train
    len_train_source = len(dset_loaders["source"])
    len_train_target = len(dset_loaders["target"])
    transfer_loss_value = classifier_loss_value = total_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        #         if i % config["test_interval"] == config["test_interval"] - 1:
        #             base_network.train(False)
        #             temp_acc = image_classification_test(dset_loaders, \
        #                 base_network, test_10crop=prep_config["test_10crop"])
        #             temp_model = nn.Sequential(base_network)
        #             if temp_acc > best_acc:
        #                 best_acc = temp_acc
        #                 best_model = temp_model
        #             log_str = "iter: {:05d}, precision: {:.5f}".format(i, temp_acc)
        #             config["out_file"].write(log_str+"\n")
        #             config["out_file"].flush()
        #             print(log_str)
        if i % config["snapshot_interval"] == 0:
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                "iter_{:05d}_model.pth.tar".format(i)))

        loss_params = config["loss"]
        ## train one iter
        base_network.train(True)
        ad_net.train(True)
        optimizer = lr_scheduler(optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        inputs_source, inputs_target, labels_source = inputs_source.cuda(
        ), inputs_target.cuda(), labels_source.cuda()
        features_source, outputs_source = base_network(inputs_source)
        features_target, outputs_target = base_network(inputs_target)
        features = torch.cat((features_source, features_target), dim=0)
        outputs = torch.cat((outputs_source, outputs_target), dim=0)
        softmax_out = nn.Softmax(dim=1)(outputs)
        if config['method'] == 'CDAN+E':
            entropy = loss.Entropy(softmax_out)
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, entropy,
                                      network.calc_coeff(i), random_layer)
        elif config['method'] == 'CDAN':
            transfer_loss = loss.CDAN([features, softmax_out], ad_net, None,
                                      None, random_layer)
        elif config['method'] == 'DANN':
            transfer_loss = loss.DANN(features, ad_net)
        else:
            raise ValueError('Method cannot be recognized.')
        classifier_loss = nn.CrossEntropyLoss()(outputs_source, labels_source)
        if i % 10 == 0:
            print('iter: ', i, 'classifier_loss: ', classifier_loss.data,
                  'transfer_loss: ', transfer_loss.data)
        total_loss = loss_params["trade_off"] * transfer_loss + classifier_loss
        total_loss.backward()
        optimizer.step()
    torch.save(best_model, osp.join(config["output_path"],
                                    "best_model.pth.tar"))
    return best_acc
def train(config):
    tie = 1.0
    ## set pre-process
    prep_dict = {}
    prep_config = config["prep"]
    prep_dict["source"] = prep.image_train( \
        resize_size=prep_config["resize_size"], \
        crop_size=prep_config["crop_size"])
    prep_dict["target"] = prep.image_train( \
        resize_size=prep_config["resize_size"], \
        crop_size=prep_config["crop_size"])
    if prep_config["test_10crop"]:
        prep_dict["test"] = prep.image_test_10crop( \
            resize_size=prep_config["resize_size"], \
            crop_size=prep_config["crop_size"])
    else:
        prep_dict["test"] = prep.image_test( \
            resize_size=prep_config["resize_size"], \
            crop_size=prep_config["crop_size"])

    ## set loss
    class_criterion = nn.CrossEntropyLoss()  # 分类损失
    transfer_criterion1 = loss.PADA  # 迁移学习损失(带权重),BCEloss
    balance_criterion = loss.balance_loss()
    loss_params = config["loss"]

    ## prepare data
    dsets = {}
    dset_loaders = {}
    data_config = config["data"]
    dsets["source"] = ImageList(open(data_config["source"]["list_path"]).readlines(), \
                                transform=prep_dict["source"])
    dset_loaders["source"] = util_data.DataLoader(dsets["source"], \
                                                  batch_size=data_config["source"]["batch_size"], \
                                                  shuffle=True, num_workers=4)
    dsets["target"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                transform=prep_dict["target"])
    dset_loaders["target"] = util_data.DataLoader(dsets["target"], \
                                                  batch_size=data_config["target"]["batch_size"], \
                                                  shuffle=True, num_workers=4)

    if prep_config["test_10crop"]:
        for i in range(10):
            dsets["test" + str(i)] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                               transform=prep_dict["test"]["val" + str(i)])
            dset_loaders["test" + str(i)] = util_data.DataLoader(dsets["test" + str(i)], \
                                                                 batch_size=data_config["test"]["batch_size"], \
                                                                 shuffle=False, num_workers=4)

            dsets["target" + str(i)] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                                 transform=prep_dict["test"]["val" + str(i)])
            dset_loaders["target" + str(i)] = util_data.DataLoader(dsets["target" + str(i)], \
                                                                   batch_size=data_config["test"]["batch_size"], \
                                                                   shuffle=False, num_workers=4)
    else:
        dsets["test"] = ImageList(open(data_config["test"]["list_path"]).readlines(), \
                                  transform=prep_dict["test"])
        dset_loaders["test"] = util_data.DataLoader(dsets["test"], \
                                                    batch_size=data_config["test"]["batch_size"], \
                                                    shuffle=False, num_workers=4)

        dsets["target_test"] = ImageList(open(data_config["target"]["list_path"]).readlines(), \
                                         transform=prep_dict["test"])
        dset_loaders["target_test"] = MyDataLoader(dsets["target_test"], \
                                                   batch_size=data_config["test"]["batch_size"], \
                                                   shuffle=False, num_workers=4)

    class_num = config["network"]["params"]["class_num"]

    ## set base network
    net_config = config["network"]
    base_network = net_config["name"](**net_config["params"])

    use_gpu = torch.cuda.is_available()
    if use_gpu:
        base_network = base_network.cuda()

    ## collect parameters
    if net_config["params"]["new_cls"]:
        if net_config["params"]["use_bottleneck"]:
            parameter_list = [{"params": base_network.feature_layers.parameters(), "lr": 1}, \
                              {"params": base_network.bottleneck.parameters(), "lr": 10}, \
                              {"params": base_network.fc.parameters(), "lr": 10}]
        else:
            parameter_list = [{"params": base_network.feature_layers.parameters(), "lr": 1}, \
                              {"params": base_network.fc.parameters(), "lr": 10}]
    else:
        parameter_list = [{"params": base_network.parameters(), "lr": 1}]

    ## add additional network for some methods
    class_weight = torch.from_numpy(np.array(
        [1.0] * class_num))  # 权重初始化为class_num维向量,初始值为1
    if use_gpu:
        class_weight = class_weight.cuda()
    ad_net = network.AdversarialNetwork(
        base_network.output_num())  # 鉴别器设置,输入为特征提取器的维数,输出为属于共域的可能性
    nad_net = network.NAdversarialNetwork(base_network.output_num())
    gradient_reverse_layer = network.AdversarialLayer(
        high_value=config["high"])
    if use_gpu:
        ad_net = ad_net.cuda()
        nad_net = nad_net.cuda()
    parameter_list.append({"params": ad_net.parameters(), "lr": 10})

    ## set optimizer
    optimizer_config = config["optimizer"]
    optimizer = optim_dict[optimizer_config["type"]](parameter_list, \
                                                     **(optimizer_config["optim_params"]))
    param_lr = []
    for param_group in optimizer.param_groups:
        param_lr.append(param_group["lr"])
    schedule_param = optimizer_config["lr_param"]
    lr_scheduler = lr_schedule.schedule_dict[optimizer_config["lr_type"]]

    ## train
    len_train_source = len(dset_loaders["source"]) - 1
    len_train_target = len(dset_loaders["target"]) - 1
    transfer_loss_value = classifier_loss_value = total_loss_value = attention_loss_value = 0.0
    best_acc = 0.0
    for i in range(config["num_iterations"]):
        if i % config["test_interval"] == 0:  # 测试
            base_network.train(False)  # 先对特征提取器进行训练
            temp_acc = image_classification_test(dset_loaders, \
                                                 base_network, test_10crop=prep_config["test_10crop"], \
                                                 gpu=use_gpu)  # 对第一个有监督训练器进行分类训练,提取特征
            temp_model = nn.Sequential(base_network)
            if temp_acc > best_acc:
                best_acc = temp_acc
                best_model = temp_model
            log_str = "iter: {:05d}, alpha: {:03f}, tradeoff: {:03f} ,precision: {:.5f}".format(
                i, loss_params["para_alpha"], loss_params["trade_off"],
                temp_acc)
            config["out_file"].write(log_str + '\n')
            config["out_file"].flush()
            print(log_str)
        if i % config["snapshot_interval"] == 0:  # 输出
            torch.save(nn.Sequential(base_network), osp.join(config["output_path"], \
                                                             "iter_{:05d}_model.pth.tar".format(i)))

        if i % loss_params["update_iter"] == loss_params["update_iter"] - 1:
            base_network.train(False)
            target_fc8_out = image_classification_predict(
                dset_loaders,
                base_network,
                softmax_param=config["softmax_param"]
            )  # 在对有监督学习进行了训练后,喂进去目标域数据,判断权重
            class_weight = torch.mean(
                target_fc8_out, 0)  # predict模型输出的预测向量取均值,为每一个体权重,将个体权重转化为类别权重
            class_weight = (class_weight /
                            torch.mean(class_weight)).cuda().view(-1)  # 归一化
            class_criterion = nn.CrossEntropyLoss(
                weight=class_weight)  # 这里的交叉熵损失函数就是带权重的

        ## train one iter
        base_network.train(True)
        optimizer = lr_scheduler(param_lr, optimizer, i, **schedule_param)
        optimizer.zero_grad()
        if i % len_train_source == 0:
            iter_source = iter(dset_loaders["source"])
        if i % len_train_target == 0:
            iter_target = iter(dset_loaders["target"])
        inputs_source, labels_source = iter_source.next()
        inputs_target, labels_target = iter_target.next()
        if use_gpu:
            inputs_source, inputs_target, labels_source = \
                Variable(inputs_source).cuda(), Variable(inputs_target).cuda(), \
                Variable(labels_source).cuda()
        else:
            inputs_source, inputs_target, labels_source = Variable(inputs_source), \
                                                          Variable(inputs_target), Variable(labels_source)

        inputs = torch.cat((inputs_source, inputs_target),
                           dim=0)  # 这里输入后一半目标域,前一半源域
        features, outputs = base_network(inputs)  # 从有分类网络获得特征与输出,到这里是特征提取器
        softmax_out = nn.Softmax(dim=1)(outputs).detach()
        ad_net.train(True)
        nad_net.train(True)
        weight_ad = torch.zeros(inputs.size(0))
        label_numpy = labels_source.data.cpu().numpy()
        for j in range(inputs.size(0) / 2):
            weight_ad[j] = class_weight[int(label_numpy[j])]  # 计算实际样例权重
        # print(label_numpy)
        weight_ad = weight_ad / torch.max(
            weight_ad[0:inputs.size(0) / 2])  # 权重归一化
        for j in range(inputs.size(0) / 2,
                       inputs.size(0)):  # 前一半源域,所以权重是计算的,后一半目标域,权重全为1
            weight_ad[j] = 1.0
        classifier_loss = class_criterion(
            outputs.narrow(0, 0,
                           inputs.size(0) / 2), labels_source)  # 分类损失
        total_loss = classifier_loss
        total_loss.backward()
        optimizer.step()

    torch.save(best_model, osp.join(config["output_path"],
                                    "best_model.pth.tar"))
    return best_acc