#meta learning# #gradient computation error# RuntimeError: one of the variables needed for gradient computation has been modified by an inplace operation

username: jsktt01
cooked: <p>I’m training the DL model under the MAML framework. But there is an error:</p>
<pre><code class="lang-python">RuntimeError: one of the variables needed for gradient computation has been modified by an inplace operation: [torch.cuda.FloatTensor [512, 1]], which is output 0 of AsStridedBackward0, is at version 4; expected version 3 instead. Hint: the backtrace further above shows the operation that failed to compute its gradient. The variable in question was changed in there or anywhere later. Good luck!
</code></pre>
<p>The simple version of MAML framework is:</p>
<pre><code class="lang-python">weights_original = deepcopy(model.state_dict())
output_support = model(input_support)
optimizer.zero_grad()
loss = criterion(output, gt_support)
loss.backward()
optimizer.step()

optimizer.zero_grad()
output_query = model(input_query)
loss = criterion(output, gt_query)
# to calculate gradients w.r.t. the initial params and update the initial params.
model.load_state_dict({name: weights_original[name] for name in weights_original})
loss.backward()
optimizer.step()
</code></pre>
<p>And for easier debugging, I use a simple model as:</p>
<pre><code class="lang-python">class Model(nn.Module):
    def __init__(self, config):
        super(Model, self).__init__()
        self.transformer_encoder = torch.nn.Linear(512, 512)
        self.transformer_decoder = torch.nn.Linear(512, 512)
    def forward(self, input):
        output = self.transformer_encoder(input)
        output = self.transformer_decoder(output)
        return output
</code></pre>
<p>When I dive into the bug, finding that if the model consists of one module, e.g. the encoder or decoder, the error disappears. But if the model include both encoder and decoder, the bug re-appears. Does anyone know the solution? THANK YOU!</p>

username: ptrblck
cooked: <p>Loading the <code>state_dict</code> will manipulate the parameters inplace and will cause the failure:</p>
<pre><code class="lang-python">model.load_state_dict({name: weights_original[name] for name in weights_original})
loss.backward()
</code></pre>
<p>Changing the parameters before calling the <code>backward</code> operation will make the forward activations stale and would otherwise compute wrong gradients.</p>
<p><a href="https://discuss.pytorch.org/t/struggling-with-a-runtime-error-related-to-in-place-operations/102222/6">This post</a> explains the issue in more detail for a GAN training, which has however the same root cause of creating stale forward activations.</p>

username: jsktt01
cooked: <p>Thanks for your reply. Actually, I need the <code>model.load_state_dict</code> operation to calculate gradients w.r.t. the initial parameters due to the mechanism of MAML.<br>
Yes, in fact when I remove the <code>model.load_state_dict</code> it works fine. But if the model has one module, such as the encoder defined above, it also works fine when calling <code>model.load_state_dict</code>. And there is one <a href="https://github.com/HLTCHKUST/PAML/blob/master/MAML.py#L156" rel="noopener nofollow ugc">public source code (line 156)</a> that has the similar operation. When I unwrap <a href="https://github.com/HLTCHKUST/PAML/blob/master/MAML.py#L150" rel="noopener nofollow ugc">the code in line 150</a>, it basically has the same pipeline as the above MAML framework.</p>