code: def __call__(
      self,
      predicted_spans: List[Tuple[int, int, str]],
      gold_spans: List[Tuple[int, int, str]],
  ) -> None:
      gold_spans = copy.copy(gold_spans)
      predicted_spans = copy.copy(predicted_spans)
      untyped_gold_spans = {(x[0], x[1]) for x in gold_spans}
      untyped_predicted_spans = {(x[0], x[1]) for x in predicted_spans}
  
      for untyped_span, span in zip(
          untyped_predicted_spans, predicted_spans
      ):
          if span in gold_spans:
              self._true_positives[span[2]] += 1
              gold_spans.remove(span)
          else:
              self._false_positives[span[2]] += 1
  
          if untyped_span in untyped_gold_spans:
              self._true_positives["untyped"] += 1
              untyped_gold_spans.remove(untyped_span)
          else:
              self._false_positives["untyped"] += 1
      # These spans weren't predicted.
      for span in gold_spans:
          self._false_negatives[span[2]] += 1
      for untyped_span in untyped_gold_spans:
          self._false_negatives["untyped"] += 1
  
file_path: scispacy/scispacy/per_class_scorer.py
imports: from typing import Dict, List, Tuple, Set
  from collections import defaultdict
  import copy
label_desc: Use image node_id 2 for calling the PerClassScorer obj's underlying member method code with example usage: obj.__call__(predicted_spans, gold_spans) without return types