class_docstr: Time series encoder. This module can learn features for any `order_by` temporal column, both with and without accompanying target data.
  
  The backbone of this encoder is either a recurrent neural network or a transformer; both structured in an encoder-decoder fashion.
class_docstr_tok: ["Time","series","encoder",".","This","module","can","learn","features","for","any","`","order_by","`","temporal","column",",","both","with","and","without","accompanying","target","data",".","The","backbone","of","this","encoder","is","either","a","recurrent","neural","network","or","a","transformer",";","both","structured","in","an","encoder-decoder","fashion","."]
docstr: Encode a list of time series data
  :param column_data: a list of (self._n_dims)-dimensional time series [[dim1_data], ...] to encode
  :param get_next_count: default None, but you can pass a number X and it will return the X following predictions
                         on the series for each ts_data_point in column_data
  :return: a list of encoded time series or if get_next_count !=0 two lists (encoded_values, projected_numbers)
docstr_tok: ["Encode","a","list","of","time","series","data",":","param","column_data",":","a","list","of","(","self._n_dims",")","-dimensional","time","series","[","[","dim1_data","]",",","...","]","to","encode",":","param","get_next_count",":","default","None",",","but","you","can","pass","a","number","X","and","it","will","return","the","X","following","predictions","on","the","series","for","each","ts_data_point","in","column_data",":","return",":","a","list","of","encoded","time","series","or","if","get_next_count","!","=0","two","lists","(","encoded_values",",","projected_numbers",")"]
code: def encode(
      self, column_data, dependency_data=None, get_next_count=None
  ):
      """
      Encode a list of time series data
      :param column_data: a list of (self._n_dims)-dimensional time series [[dim1_data], ...] to encode
      :param get_next_count: default None, but you can pass a number X and it will return the X following predictions
                             on the series for each ts_data_point in column_data
      :return: a list of encoded time series or if get_next_count !=0 two lists (encoded_values, projected_numbers)
      """
  
      if not self.is_prepared:
          raise Exception(
              'You need to call "prepare" before calling "encode" or "decode".'
          )
  
      if isinstance(column_data, pd.Series):
          data = deepcopy(
              column_data.values
          )  # get a copy to avoid modifying the actual data frame
      else:
          data = column_data
  
      for i in range(len(data)):
          if not isinstance(data[i][0], list):
              data[i] = [data[i]]  # add dimension for 1D timeseries
  
      # include autoregressive target data
      ptd = []
      if dependency_data is not None:
          for dep, dep_data in dependency_data.items():
              if dep in self.grouped_by:
                  continue
              # normalize numerical target per group-by
              if self._target_type in (
                  dtype.integer,
                  dtype.float,
                  dtype.num_tsarray,
              ):
                  dep_info = {
                      "group_info": {
                          group: dependency_data[group]
                          for group in self.grouped_by
                      },
                      "data": dep_data,
                  }
                  tensor = torch.zeros(
                      (len(dep_data), len(dep_data[0]), 1)
                  ).to(self.device)
                  all_idxs = set(range(len(dep_data)))
  
                  grouped = dep_info["data"].groupby(by=self.grouped_by)
                  for combination in [
                      c
                      for c in self._group_combinations
                      if c != "__default"
                  ]:
                      normalizer = self.dep_norms[dep].get(
                          tuple(combination), None
                      )
                      if normalizer is None:
                          normalizer = self.dep_norms[dep]["__default"]
                      subdf = grouped.get_group(normalizer.combination)
                      tensor[subdf.index, :, :] = (
                          torch.Tensor(normalizer.encode(subdf))
                          .unsqueeze(-1)
                          .to(self.device)
                      )
                      all_idxs -= set(subdf.index)
  
                  # encode all remaining rows (not belonging to any grouped combination) with default normalizer
                  if all_idxs:
                      default_norm = self.dep_norms[dep]["__default"]
                      subset = [dep_data[idx] for idx in all_idxs]
                      tensor[list(all_idxs), :, :] = (
                          torch.Tensor(default_norm.encode(subset))
                          .unsqueeze(-1)
                          .to(self.device)
                      )
                      tensor[torch.isnan(tensor)] = 0.0
  
              # normalize categorical target
              else:
                  normalizer = self.dep_norms[dep]["__default"]
                  tensor = normalizer.encode(dep_data)
                  tensor[torch.isnan(tensor)] = 0.0
  
              ptd.append(tensor)
  
      ret = []
      next = []
  
      for i, val in enumerate(data):
          if get_next_count is None:
              if (
                  dependency_data is not None
                  and len(dependency_data) > 0
                  and len(ptd) > 0
              ):
                  encoded = self._encode_one(
                      val, previous=[values[i] for values in ptd]
                  )
              else:
                  encoded = self._encode_one(val)
  
          else:
              if get_next_count <= 0:
                  raise Exception(
                      "get_next_count must be greater than 0"
                  )
  
              hidden = None
              vector = val
              next_i = []
  
              for j in range(get_next_count):
                  hidden, next_reading = self._encode_one(
                      vector,
                      initial_hidden=hidden,
                      return_next_value=True,
                  )
                  vector = [next_reading]
                  if j == 0:
                      encoded = hidden
                  next_i.append(next_reading)
  
              next_value = next_i[0][0].cpu()
  
              if self._normalizer:
                  next_value = torch.Tensor(
                      self._normalizer.decode(next_value)
                  )
  
              next.append(next_value)
  
          ret.append(encoded[0][0].cpu())
  
      if get_next_count is None:
          return torch.stack(ret)
      else:
          return torch.stack(ret), torch.stack(next)
  
imports: import time
  from math import gcd
  from typing import List
  from copy import deepcopy
  import numpy
  import pandas
  import torch
  import torch.nn
  from torch import optim
  from type_infer.dtype import dtype
  from lightwood.helpers.log import log
  from lightwood.encoder.base import BaseEncoder
  from lightwood.helpers.device import get_device_from_name
  from lightwood.helpers.torch import LightwoodAutocast
  from lightwood.encoder.datetime import DatetimeNormalizerEncoder
  from lightwood.encoder.time_series.helpers.rnn_helpers import EncoderRNNNumerical, DecoderRNNNumerical
  from lightwood.encoder.helpers import MinMaxNormalizer, CatNormalizer
  from lightwood.encoder.time_series.helpers.transformer_helpers import TransformerEncoder, get_chunk, len_to_mask
label_desc: Use image node_id 8 for calling the TimeSeriesEncoder obj's underlying member method code with example usage: obj.encode(column_data, dependency_data, get_next_count) and returns: torch, torch,  torch