How to fix 'Expected object of scalar type Float but got scalar type Double for argument #4 'mat1''?
I am trying to build an lstm model. My model code is below.

My input has 4 features, Sequence length of 5 and batch size of 32.

        class RNN(nn.Module):

            def __init__(self, feature_dim, output_size, hidden_dim, n_layers, dropout=0.5):
                """
                Initialize the PyTorch RNN Module
                :param feature_dim: The number of input dimensions of the neural network
                :param output_size: The number of output dimensions of the neural network      
                :param hidden_dim: The size of the hidden layer outputs
                :param dropout: dropout to add in between LSTM/GRU layers
                """
                super(RNN, self).__init__()

                # set class variables
                self.output_size = output_size
                self.n_layers = n_layers
                self.hidden_dim = hidden_dim

                # define model layers
                self.lstm = nn.LSTM(feature_dim, hidden_dim, n_layers, batch_first=True)

                self.fc = nn.Linear(hidden_dim, output_size)

                self.dropout = nn.Dropout(dropout)


            def forward(self, nn_input, hidden):
                """
                Forward propagation of the neural network
                :param nn_input: The input to the neural network
                :param hidden: The hidden state        
                :return: Two Tensors, the output of the neural network and the latest hidden state
                """

                # Get Batch Size  
                batch_size = nn_input.size(0)

                # Pass through LSTM layer
                lstm_out, hidden = self.lstm(nn_input, hidden)
                # Stack up LSTM outputs
                lstm_out = lstm_out.contiguous().view(-1, self.hidden_dim)
                # Add dropout and pass through fully connected layer
                x = self.dropout(lstm_out)
                x = self.fc(lstm_out)

                # reshape to be batch_size first
                output = x.view(batch_size, -1, self.output_size)
                # get last batch of labels
                out = output[:, -1]

                # return one batch of output word scores and the hidden state
                return out, hidden


            def init_hidden(self, batch_size):
                '''
                Initialize the hidden state of an LSTM/GRU
                :param batch_size: The batch_size of the hidden state
                :return: hidden state of dims (n_layers, batch_size, hidden_dim)
                '''
                # Implement function

                # initialize   state with zero weights, and move to GPU if available
                weight = next(self.parameters()).data

                if is_gpu_available:
                    hidden = (weight.new(self.n_layers, batch_size, self.hidden_dim).zero_().to(device),
                          weight.new(self.n_layers, batch_size, self.hidden_dim).zero_().to(device))
                else:
                    hidden = (weight.new(self.n_layers, batch_size, self.hidden_dim).zero_(),
                              weight.new(self.n_layers, batch_size, self.hidden_dim).zero_())
                return hidden


When I train, I got the error

RuntimeError                              Traceback (most recent call last)
    /usr/local/bin/kernel-launchers/python/scripts/launch_ipykernel.py in &lt;module&gt;
          3 
          4 # training the model
    ----&gt; 5 trained_rnn = train_rnn(rnn, batch_size, optimizer, num_epochs, show_every_n_batches)
          6 
          7 # saving the trained model

    /usr/local/bin/kernel-launchers/python/scripts/launch_ipykernel.py in train_rnn(rnn, batch_size, optimizer, n_epochs, show_every_n_batches)
         18 
         19             # forward, back prop
    ---&gt; 20             loss, hidden = forward_back_prop(rnn, optimizer, inputs, labels, hidden)
         21             # record loss
         22             batch_losses.append(loss)

    /usr/local/bin/kernel-launchers/python/scripts/launch_ipykernel.py in forward_back_prop(rnn, optimizer, inp, target, hidden)
         22 
         23     # get the output from the model
    ---&gt; 24     output, h = rnn(inp, h)
         25 
         26    # calculate the loss and perform backprop

    /usr/local/lib/python3.7/dist-packages/torch/nn/modules/module.py in __call__(self, *input, **kwargs)
        491             result = self._slow_forward(*input, **kwargs)
        492         else:
    --&gt; 493             result = self.forward(*input, **kwargs)
        494         for hook in self._forward_hooks.values():
        495             hook_result = hook(self, input, result)

    /usr/local/bin/kernel-launchers/python/scripts/launch_ipykernel.py in forward(self, nn_input, hidden)
         36 
         37         # Pass through LSTM layer
    ---&gt; 38         lstm_out, hidden = self.lstm(nn_input, hidden)
         39         # Stack up LSTM outputs
         40         lstm_out = lstm_out.contiguous().view(-1, self.hidden_dim)

    /usr/local/lib/python3.7/dist-packages/torch/nn/modules/module.py in __call__(self, *input, **kwargs)
        491             result = self._slow_forward(*input, **kwargs)
        492         else:
    --&gt; 493             result = self.forward(*input, **kwargs)
        494         for hook in self._forward_hooks.values():
        495             hook_result = hook(self, input, result)

    /usr/local/lib/python3.7/dist-packages/torch/nn/modules/rnn.py in forward(self, input, hx)
        557             return self.forward_packed(input, hx)
        558         else:
    --&gt; 559             return self.forward_tensor(input, hx)
        560 
        561 

    /usr/local/lib/python3.7/dist-packages/torch/nn/modules/rnn.py in forward_tensor(self, input, hx)
        537         unsorted_indices = None
        538 
    --&gt; 539         output, hidden = self.forward_impl(input, hx, batch_sizes, max_batch_size, sorted_indices)
        540 
        541         return output, self.permute_hidden(hidden, unsorted_indices)

    /usr/local/lib/python3.7/dist-packages/torch/nn/modules/rnn.py in forward_impl(self, input, hx, batch_sizes, max_batch_size, sorted_indices)
        520         if batch_sizes is None:
        521             result = _VF.lstm(input, hx, self._get_flat_weights(), self.bias, self.num_layers,
    --&gt; 522                               self.dropout, self.training, self.bidirectional, self.batch_first)
        523         else:
        524             result = _VF.lstm(input, batch_sizes, hx, self._get_flat_weights(), self.bias,

    RuntimeError: Expected object of scalar type Float but got scalar type Double for argument #4 'mat1'     


I am not able to figure the cause of this error. How to fix it? Please help.

Also, is it the correct way of implementing the LSTM or is there a better way to achieve the same?

torch.nn.LSTM does not need any initialization, as it's initialized to zeros by default (see documentation).
Furthermore, torch.nn.Module already has predefined cuda() method, so one can move module to GPU simply, hence you can safely delete init_hidden(self, batch_size).

You have this error because your input is of type torch.Double, while modules by default use torch.Float (as it's accurate enough, faster and smaller than torch.Double).
You can cast your input Tensors by calling .float(), in your case it could look like that:

def forward(self, nn_input, hidden):
    nn_input = nn_input.float()
    ... # rest of your code


Finally, there is no need for hidden argument if it's always zeroes, you can simply use:

lstm_out, hidden = self.lstm(nn_input) # no hidden here


as hidden is zeroes by default as well.
