code: def n_k_filter(
      a: np.ndarray,
      num_open: int,
      num_clear: int,
      num_open_suff: Optional[int] = None,
      num_clear_suff: Optional[int] = None,
      initial_label: int = 0,
      forward_fill: bool = False,
  ) -> np.ndarray:
      """
      Implements the (N, K)-filter that opens/closes anomalies based on observing
      K or greater labels in the last N time steps.
  
      Parameters
      ----------
      a
          input array, type boolean
      num_open
          number of time steps to look back for opening an anomaly
      num_clear
          number of time steps to look back for clearing an anomaly
      num_open_suff
          number of positive labels in the lookback period sufficient
          to open an anomaly. defaults to num_open.
      num_clear_suff
          number of positive labels in the lookback period sufficient
          to clear an anomaly. defaults to num_clear.
      initial_label
          1 if the initial state is an anomaly, 0 if not. default 0.
      """
      num_open_suff = num_open_suff or num_open
      num_clear_suff = num_clear_suff or num_clear
  
      if forward_fill:
          a = fill_forward(a)
  
      def causal_conv(a, f):
          if len(f) > 1:
              return np.convolve(a, f)[: -(len(f) - 1)]
          return np.convolve(a, f)
  
      up = causal_conv(a > 0, np.ones(num_open)) >= num_open_suff
      down = causal_conv(a == 0, np.ones(num_clear)) >= num_clear_suff
  
      s = initial_label
      out = []
      for i in range(len(up)):
          s = up[i] if s == 0 else ~down[i]
          out.append(s)
      return np.array(out, dtype=int)
  
imports: from typing import Optional
  import numpy
label_desc: Use image node_id 3 for calling a global function with example usage: n_k_filter(a, num_open, num_clear, num_open_suff, num_clear_suff, initial_label, forward_fill) and returns: np, np, np