Module monk.pytorch.models.common
Expand source code
from pytorch.models.imports import *
from system.imports import *
from pytorch.models.layers import get_layer
def set_parameter_requires_grad(finetune_net, freeze_base_network):
    '''
    Freeze based network as per params set
    Args:
        finetune_net (network): Model network
        freeze_base_network (bool): If True, all trainable params are freezed
    Returns:
        network: Updated Model network
    '''
    if freeze_base_network:
        for param in finetune_net.parameters():
            param.requires_grad = False
    else:
        for param in finetune_net.parameters():
            param.requires_grad = True
    return finetune_net
def set_final_layer(custom_network, num_ftrs, num_classes):
    '''
    Setup final sub-network 
    Args:
        custom_network (list): List of dicts containing details on appeded layers to base netwoek in transfer learning
        num_ftrs (int): Number of features coming from base network's last layers
        num_classes (int): Number of classes in the dataset
    Returns:
        layer: Sequential sub-network with added layers 
    '''
    modules = [];
    for i in range(len(custom_network)):
        layer, num_ftrs = get_layer(custom_network[i], num_ftrs);
        modules.append(layer);
    sequential = nn.Sequential(*modules)
    return sequential;
def create_final_layer(finetune_net, custom_network, num_classes, set=1):
    '''
    Create final sub-network 
    Args:
        finetune_net (network): Initial base network
        custom_network (list):  List of dicts containing details on appeded layers to base netwoek in transfer learning
        num_classes (int): Number of classes in the dataset
        set (int): Select the right set to find the details of outermost layer
    Returns:
        network: Updated base network with appended custom additions
    '''
    if(set == 1):
        num_ftrs = finetune_net.classifier[6].in_features;
        finetune_net.classifier = set_final_layer(custom_network, num_ftrs, num_classes);
    elif(set == 2):
        num_ftrs = finetune_net.classifier.in_features;
        finetune_net.classifier = set_final_layer(custom_network, num_ftrs, num_classes);
    elif(set == 3):
        num_ftrs = finetune_net.fc.in_features;
        finetune_net.fc = set_final_layer(custom_network, num_ftrs, num_classes);
    elif(set == 4):
        num_ftrs = finetune_net.classifier[1].in_features;
        finetune_net.classifier = set_final_layer(custom_network, num_ftrs, num_classes);
    
    return finetune_net;
def model_to_device(system_dict):
    '''
    Load model weights on device - cpu or gpu 
    Args:
        system_dict (dict): System dict containing system state and parameters
    Returns:
        dict: Updated system dict 
    '''
    if(system_dict["model"]["params"]["use_gpu"]):
        system_dict["local"]["device"] = torch.device("cuda:0" if torch.cuda.is_available() else "cpu");
        if(torch.cuda.is_available()):
            use_gpu = True;
            system_dict["model"]["params"]["use_gpu"] = use_gpu;
        else:
            use_gpu = False;
            system_dict["model"]["params"]["use_gpu"] = use_gpu;
    else:
        system_dict["local"]["device"] = torch.device("cpu");
    
    system_dict["local"]["model"] = system_dict["local"]["model"].to(system_dict["local"]["device"]);
    return system_dict;
def print_grad_stats(system_dict):
    '''
    Print details on which layers are trainable
    Args:
        system_dict (dict): System dict containing system state and parameters
    Returns:
        None 
    '''
    print("Model - Gradient Statistics");
    i = 1;
    for name, param in system_dict["local"]["model"].named_parameters():
        if(i%2 != 0):
            print("    {}. {} Trainable - {}".format(i//2+1, name, param.requires_grad ));
        i += 1;
    print("");
def get_num_layers(system_dict):
    '''
    Get number of potentially trainable layers
    Args:
        system_dict (dict): System dict containing system state and parameters
    Returns:
        dict: Updated system dict 
    '''
    num_layers = 0;
    layer_names = [];
    for param in system_dict["local"]["model"].named_parameters():
        lname = ".".join(param[0].split(".")[:-1]);
        if lname not in layer_names:
            layer_names.append(lname)
    num_layers = len(layer_names);
    system_dict["model"]["params"]["num_layers"] = num_layers;
    return system_dict;
def freeze_layers(num, system_dict):
    '''
    Main function responsible to freeze layers in network
    Args:
        num (int): Number of layers to freeze
        system_dict (dict): System dict containing system state and parameters
    Returns:
        dict: Updated system dict 
    '''
    system_dict = get_num_layers(system_dict);
    num_layers_in_model = system_dict["model"]["params"]["num_layers"];
    if(num > num_layers_in_model):
        msg = "Parameter num > num_layers_in_model\n";
        msg += "Freezing entire network\n";
        msg += "TIP: Total layers: {}".format(num_layers_in_model);
        raise ConstraintError(msg)
    current_num = 0;
    value = False;
    layer_names = [];
    for name,param in system_dict["local"]["model"].named_parameters():
        param.requires_grad = value;
        lname = ".".join(name.split(".")[:-1]);
        if lname not in layer_names:
            layer_names.append(lname);
            current_num += 1;
        if(current_num == num):
            value = True;
    system_dict["local"]["params_to_update"] = []
    layer_names = [];
    for name, param in self.system_dict["local"]["model"].named_parameters():
        if param.requires_grad == True:
            self.system_dict["local"]["params_to_update"].append(param);
            lname = ".".join(name.split(".")[:-1]);
            if lname not in layer_names:
                layer_names.append(lname);
    self.system_dict["model"]["params"]["num_params_to_update"] = len(layer_names);
    system_dict["model"]["status"] = True;
    return system_dict;
def get_layer_uid(network_stack, count):
    '''
    Get a unique name for layer in custom network development
    Args:
        network_stack (list): List of list containing custom network details
        count (dict): a unique dictionary mapping number of every type of layer in the network
        system_dict (dict): System dict containing system state and parameters
    Returns:
        str: layer unique name
        dict: updated layer type mapper count
    '''
    if network_stack["uid"]:
        return network_stack["uid"], count;
    else:
        index = layer_names.index(network_stack["name"]);
        network_name = names[index] + str(count[index]);
        count[index] += 1;
        return network_name, count;
Functions
def create_final_layer(finetune_net, custom_network, num_classes, set=1)- 
Create final sub-network
Args
finetune_net:network- Initial base network
 custom_network:list- List of dicts containing details on appeded layers to base netwoek in transfer learning
 num_classes:int- Number of classes in the dataset
 set:int- Select the right set to find the details of outermost layer
 
Returns
network- Updated base network with appended custom additions
 
Expand source code
def create_final_layer(finetune_net, custom_network, num_classes, set=1): ''' Create final sub-network Args: finetune_net (network): Initial base network custom_network (list): List of dicts containing details on appeded layers to base netwoek in transfer learning num_classes (int): Number of classes in the dataset set (int): Select the right set to find the details of outermost layer Returns: network: Updated base network with appended custom additions ''' if(set == 1): num_ftrs = finetune_net.classifier[6].in_features; finetune_net.classifier = set_final_layer(custom_network, num_ftrs, num_classes); elif(set == 2): num_ftrs = finetune_net.classifier.in_features; finetune_net.classifier = set_final_layer(custom_network, num_ftrs, num_classes); elif(set == 3): num_ftrs = finetune_net.fc.in_features; finetune_net.fc = set_final_layer(custom_network, num_ftrs, num_classes); elif(set == 4): num_ftrs = finetune_net.classifier[1].in_features; finetune_net.classifier = set_final_layer(custom_network, num_ftrs, num_classes); return finetune_net; def freeze_layers(num, system_dict)- 
Main function responsible to freeze layers in network
Args
num:int- Number of layers to freeze
 system_dict:dict- System dict containing system state and parameters
 
Returns
dict- Updated system dict
 
Expand source code
def freeze_layers(num, system_dict): ''' Main function responsible to freeze layers in network Args: num (int): Number of layers to freeze system_dict (dict): System dict containing system state and parameters Returns: dict: Updated system dict ''' system_dict = get_num_layers(system_dict); num_layers_in_model = system_dict["model"]["params"]["num_layers"]; if(num > num_layers_in_model): msg = "Parameter num > num_layers_in_model\n"; msg += "Freezing entire network\n"; msg += "TIP: Total layers: {}".format(num_layers_in_model); raise ConstraintError(msg) current_num = 0; value = False; layer_names = []; for name,param in system_dict["local"]["model"].named_parameters(): param.requires_grad = value; lname = ".".join(name.split(".")[:-1]); if lname not in layer_names: layer_names.append(lname); current_num += 1; if(current_num == num): value = True; system_dict["local"]["params_to_update"] = [] layer_names = []; for name, param in self.system_dict["local"]["model"].named_parameters(): if param.requires_grad == True: self.system_dict["local"]["params_to_update"].append(param); lname = ".".join(name.split(".")[:-1]); if lname not in layer_names: layer_names.append(lname); self.system_dict["model"]["params"]["num_params_to_update"] = len(layer_names); system_dict["model"]["status"] = True; return system_dict; def get_layer_uid(network_stack, count)- 
Get a unique name for layer in custom network development
Args
network_stack:list- List of list containing custom network details
 count:dict- a unique dictionary mapping number of every type of layer in the network
 system_dict:dict- System dict containing system state and parameters
 
Returns
str- layer unique name
 dict- updated layer type mapper count
 
Expand source code
def get_layer_uid(network_stack, count): ''' Get a unique name for layer in custom network development Args: network_stack (list): List of list containing custom network details count (dict): a unique dictionary mapping number of every type of layer in the network system_dict (dict): System dict containing system state and parameters Returns: str: layer unique name dict: updated layer type mapper count ''' if network_stack["uid"]: return network_stack["uid"], count; else: index = layer_names.index(network_stack["name"]); network_name = names[index] + str(count[index]); count[index] += 1; return network_name, count; def get_num_layers(system_dict)- 
Get number of potentially trainable layers
Args
system_dict:dict- System dict containing system state and parameters
 
Returns
dict- Updated system dict
 
Expand source code
def get_num_layers(system_dict): ''' Get number of potentially trainable layers Args: system_dict (dict): System dict containing system state and parameters Returns: dict: Updated system dict ''' num_layers = 0; layer_names = []; for param in system_dict["local"]["model"].named_parameters(): lname = ".".join(param[0].split(".")[:-1]); if lname not in layer_names: layer_names.append(lname) num_layers = len(layer_names); system_dict["model"]["params"]["num_layers"] = num_layers; return system_dict; def model_to_device(system_dict)- 
Load model weights on device - cpu or gpu
Args
system_dict:dict- System dict containing system state and parameters
 
Returns
dict- Updated system dict
 
Expand source code
def model_to_device(system_dict): ''' Load model weights on device - cpu or gpu Args: system_dict (dict): System dict containing system state and parameters Returns: dict: Updated system dict ''' if(system_dict["model"]["params"]["use_gpu"]): system_dict["local"]["device"] = torch.device("cuda:0" if torch.cuda.is_available() else "cpu"); if(torch.cuda.is_available()): use_gpu = True; system_dict["model"]["params"]["use_gpu"] = use_gpu; else: use_gpu = False; system_dict["model"]["params"]["use_gpu"] = use_gpu; else: system_dict["local"]["device"] = torch.device("cpu"); system_dict["local"]["model"] = system_dict["local"]["model"].to(system_dict["local"]["device"]); return system_dict; def print_grad_stats(system_dict)- 
Print details on which layers are trainable
Args
system_dict:dict- System dict containing system state and parameters
 
Returns
None
Expand source code
def print_grad_stats(system_dict): ''' Print details on which layers are trainable Args: system_dict (dict): System dict containing system state and parameters Returns: None ''' print("Model - Gradient Statistics"); i = 1; for name, param in system_dict["local"]["model"].named_parameters(): if(i%2 != 0): print(" {}. {} Trainable - {}".format(i//2+1, name, param.requires_grad )); i += 1; print(""); def set_final_layer(custom_network, num_ftrs, num_classes)- 
Setup final sub-network
Args
custom_network:list- List of dicts containing details on appeded layers to base netwoek in transfer learning
 num_ftrs:int- Number of features coming from base network's last layers
 num_classes:int- Number of classes in the dataset
 
Returns
layer- Sequential sub-network with added layers
 
Expand source code
def set_final_layer(custom_network, num_ftrs, num_classes): ''' Setup final sub-network Args: custom_network (list): List of dicts containing details on appeded layers to base netwoek in transfer learning num_ftrs (int): Number of features coming from base network's last layers num_classes (int): Number of classes in the dataset Returns: layer: Sequential sub-network with added layers ''' modules = []; for i in range(len(custom_network)): layer, num_ftrs = get_layer(custom_network[i], num_ftrs); modules.append(layer); sequential = nn.Sequential(*modules) return sequential; def set_parameter_requires_grad(finetune_net, freeze_base_network)- 
Freeze based network as per params set
Args
finetune_net:network- Model network
 freeze_base_network:bool- If True, all trainable params are freezed
 
Returns
network- Updated Model network
 
Expand source code
def set_parameter_requires_grad(finetune_net, freeze_base_network): ''' Freeze based network as per params set Args: finetune_net (network): Model network freeze_base_network (bool): If True, all trainable params are freezed Returns: network: Updated Model network ''' if freeze_base_network: for param in finetune_net.parameters(): param.requires_grad = False else: for param in finetune_net.parameters(): param.requires_grad = True return finetune_net