docs: def make_encoder(self,formula_dict,inter_list,param_dict):
          """
          make the encoder function
          """
          X_dict = {}
          Xcol_dict = {}
          encoder_dict = {}
          # first, replace param_dict[key] = values, with param_dict[key] = dmatrix
          for key in formula_dict:
              encoding,arg = formula_dict[key]
              if 'Dev' in encoding:
                  # make deviation encoded design matrix
                  drop_name = arg
                  # encode
                  deviation_encoder,X_sub,colnames_sub = _dev_encode(param_dict,drop_name,key)
                  # additionally, store in dictionary for use by interactions
                  X_dict[key] = X_sub
                  Xcol_dict[key] = colnames_sub
                  # store dictionary of encoder functions to keep for prediction
                  encoder_dict[key] = deviation_encoder
              elif 'Dum' in encoding:
                  # make dummy variable encoding design mat
                  ref_name = arg
                  dummy_encoder,X_sub,colnames_sub = _dum_encode(param_dict,ref_name,key)
                  # additionally, store in dictionary for use by interactions
                  X_dict[key] = X_sub
                  Xcol_dict[key] = colnames_sub
                  # store dictionary of encoder functions to keep for prediction
                  encoder_dict[key] = dummy_encoder
              elif 'Poly' in encoding:
                  # make polynomial encoding design mat
                  degree = arg
                  polynomial_encoder,X_sub,colnames_sub = _poly_encode(param_dict,degree,key)
                  # additionally, store in dictionary for use by interactions
                  X_dict[key] = X_sub
                  Xcol_dict[key] = colnames_sub
                  # store dictionary of encoder functions to keep for prediction
                  encoder_dict[key] = polynomial_encoder
              else:
                  print encoding
                  raise Exception("Encoding name error")
          # now compute interaction designmatrices
          for interaction in inter_list:
              if len(interaction) >= 3:
                  raise Exception("Doesn't allow 4-way or higher interaction terms")
              elif len(interaction) == 3:
  
                  param_name1 = interaction[0]
                  param_name2 = interaction[1]
                  param_name3 = interaction[2]
                  col_names1 = Xcol_dict[param_name1]
                  col_names2 = Xcol_dict[param_name2]
                  col_names3 = Xcol_dict[param_name3]
  
                  # make 3-way encoder function
                  def threeway_encoder(param_name1,param_name2,param_name3, \
                                       col_names1, col_names2, col_names3, X_dict):
                      """
                      needs the three names of the parameters to be encoded, as well as
                      a dictionary containing the already encoded single parameter 
                      design matrices, keyed by name
                      """
                      X1 = X_dict[param_name1]
                      X2 = X_dict[param_name2]
                      X3 = X_dict[param_name3]
  
                      X_int = []
                      names_int = []
                      for i in np.arange(0,X1.shape[1]):
                          for j in np.arange(0,X2.shape[1]):
                              for k in np.arange(0,X3.shape[1]):
                                  X_int.append(X1[:,i]*X2[:,j]*X3[:,k])
                                  names_int.append(col_names1[i] + "*" + \
                                                   col_names2[j] + "*" + col_names3[k])
                      # make X_int from lists to np array
                      X_int = np.array(X_int).T
                      return X_int, names_int
                  encoder_dict['threeway'] = threeway_encoder
  
              elif len(interaction) == 2:
                  # there are two interaction terms (A*B)
  
                  param_name1 = interaction[0]
                  param_name2 = interaction[1]
                  col_names1  = Xcol_dict[param_name1]
                  col_names2  = Xcol_dict[param_name2]
  
                  # make twoway_encoder function
                  def twoway_encoder(param_name1,param_name2, col_names1, col_names2, X_dict):
                      X1 = X_dict[param_name1]
                      X2 = X_dict[param_name2]
  
                      X_int = []
                      names_int = []
                      for i in np.arange(0,X1.shape[1]):
                          for j in np.arange(0,X2.shape[1]):
                              X_int.append(X1[:,i]*X2[:,j])
                              names_int.append(col_names1[i] + "*" + col_names2[j])
                      X_int = np.array(X_int).T
                      return X_int, names_int
                  encoder_dict['twoway'] = twoway_encoder
              else:
                  raise Exception("Error while evaluating meaning of interaction term")
  
          # make key in encoder to specify which columns are active
          encoder_dict['trimmed_columns'] = self._trimmed_columns
          return encoder_dict