-
Notifications
You must be signed in to change notification settings - Fork 0
/
cnn_hpc.py
executable file
·147 lines (109 loc) · 4.75 KB
/
cnn_hpc.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Mon Nov 29 11:03:46 2021
@author: simon
"""
import numpy as np
from importlib import reload
import sys
import torch
import torch.nn as nn
import helper_functions
reload(helper_functions)
from helper_functions import accuracy_rate, load_data, capacity, get_good_idx, get_slice, get_k_fold_cv_idx, get_x_sequences_cnn, train, get_all_accuracy_rates, allocate_x_batch_cnn, quantile_score, get_competition_preds
import argparse
import sys
import os
parser=argparse.ArgumentParser()
parser.add_argument('--num_hidden', help='Integer number of hidden layers', type=int)
parser.add_argument('--kernel_size', help='Integer size of kernel', type=int)
parser.add_argument('--pred_seq_len', help='Integer number of time steps for each prediction',type=int)
parser.add_argument('--loss', help='Training loss metric, either MSE or L1',type=str)
parser.add_argument('--weight_decay', help='weight_decay, float',type=float)
parser.add_argument('--dropout', help='dropout, float',type=float)
parser.add_argument('--case', help='case, int',type=int)
parser.add_argument('--drop_cols', help='dataframe columns to drop',type=str, default='')
# args = parser.parse_args("--num_hidden=2 --kernel_size=7 --pred_seq_len=25 --loss=MSE --weight_decay=0.01 --dropout=0.1 --case=1".split())
args = parser.parse_args()
num_hidden = args.num_hidden
pred_seq_len = args.pred_seq_len
kernel_size = args.kernel_size
loss = args.loss
weight_decay = args.weight_decay
drop_p = args.dropout
case = args.case
drop_cols = args.drop_cols
#assert torch.cuda.is_available()
outfolder = 'training results'
outfile = f'cnn_{"_".join(sys.argv[1:]).replace("=","_")}.npz'.lower()
if outfile in os.listdir(outfolder):
print(f'File {outfile} already exists. Exits.')
sys.exit()
nn_type = 'cnn'
allocate_x_batch = allocate_x_batch_cnn
get_x_sequences = get_x_sequences_cnn
np.random.seed(2021)
cols_to_drop = []
drop_col_name_dict={'power_curve':('Speed_50m_power_curve','Speed_100m_power_curve'), 'cubed':('Speed_50m_cubed','Speed_100m_cubed'),'season':('season_cos','season_sin'),'time':('time_day_cos','time_day_sin')}
for substring in drop_col_name_dict.keys():
if substring in drop_cols.lower():
cols_to_drop.extend(drop_col_name_dict[substring])
x,x_time,y,y_time,time_dif,idx_offset = load_data(case, cols_to_drop)
# Index offset between start and end of training data for one single prediction
# i.e. number of quarters of an hour we wish to train on for each sample
good_idx = get_good_idx(x,y,idx_offset,pred_seq_len)
input_size = x.shape[1]
num_channels = input_size
out_size = 1
stride = 1
padding = kernel_size//2
conv_out_seq = round((pred_seq_len + 2*padding - kernel_size) / stride + 1)
# define network
class Net(nn.Module):
def __init__(self):
super(Net, self).__init__()
self.conv_in = nn.Conv1d(in_channels = input_size,
out_channels = num_channels,
kernel_size = kernel_size,
stride=stride,
padding=padding,
groups = input_size)
self.hidden_list=nn.ModuleList()
for i in range(num_hidden):
self.hidden_list.append(nn.Conv1d(in_channels = num_channels,
out_channels = num_channels,
kernel_size = kernel_size,
stride=stride,
padding=padding,
groups = input_size))
self.l_out = nn.Linear(in_features=conv_out_seq * num_channels,
out_features=out_size,
bias=True)
self.act = nn.ReLU()
self.dropout = nn.Dropout(p=drop_p)
def forward(self, x):
x = self.conv_in(x)
for hidden_layer in self.hidden_list:
x = hidden_layer(x)
x = self.dropout(x)
x = self.act(x)
x = x.reshape(-1, conv_out_seq * num_channels)
x = self.dropout(x)
x = self.act(x)
x = self.l_out(x)
return x
# setting hyperparameters and gettings epoch sizes
batch_size = 10000
num_epochs = 50
k_fold_size = 6
if loss.lower() == 'mse':
loss = nn.MSELoss()
elif loss.lower() == 'l1':
loss = nn.L1Loss()
else:
raise(Exception('unrecognized loss function'))
optim_params = {'lr': 3e-3, 'weight_decay': weight_decay}
train_loss, valid_loss, net = train(nn_type, x, y, Net, optim_params, num_epochs, batch_size, good_idx, k_fold_size, idx_offset, pred_seq_len, loss, case)
valid_loss[0] = np.sqrt(valid_loss[0])
np.savez(os.path.join(outfolder, outfile), train_loss=train_loss, valid_loss=valid_loss)