When trying to create a neural network and optimize it using Pytorch, I am getting
ValueError: optimizer got an empty parameter list
Here is the code.
import torch.nn as nn
import torch.nn.functional as F
from os.path import dirname
from os import getcwd
from os.path import realpath
from sys import argv
class NetActor(nn.Module):
def __init__(self, args, state_vector_size, action_vector_size, hidden_layer_size_list):
super(NetActor, self).__init__()
self.args = args
self.state_vector_size = state_vector_size
self.action_vector_size = action_vector_size
self.layer_sizes = hidden_layer_size_list
self.layer_sizes.append(action_vector_size)
self.nn_layers = []
self._create_net()
def _create_net(self):
prev_layer_size = self.state_vector_size
for next_layer_size in self.layer_sizes:
next_layer = nn.Linear(prev_layer_size, next_layer_size)
prev_layer_size = next_layer_size
self.nn_layers.append(next_layer)
def forward(self, torch_state):
activations = torch_state
for i,layer in enumerate(self.nn_layers):
if i != len(self.nn_layers)-1:
activations = F.relu(layer(activations))
else:
activations = layer(activations)
probs = F.softmax(activations, dim=-1)
return probs
and then the call
self.actor_nn = NetActor(self.args, 4, 2, [128])
self.actor_optimizer = optim.Adam(self.actor_nn.parameters(), lr=args.learning_rate)
gives the very informative error
ValueError: optimizer got an empty parameter list
I find it hard to understand what exactly in the network's definition makes the network have parameters.
I am following and expanding the example I found in Pytorch's tutorial code.
I can't really tell the difference between my code and theirs that makes mine think it has no parameters to optimize.
How to make my network have parameters like the linked example?
Your
NetActor
does not directly store anynn.Parameter
. Moreover, all other layers it eventually uses inforward
are stored as a simple list isself.nn_layers
.If you want
self.actor_nn.parameters()
to know that the items stored in the listself.nn_layers
may contain trainable parameters, you should work with containers.Specifically, making
self.nn_layers
to be ann.ModuleList
instead of a simple list should solve your problem: