class_docstr: Calculate affinities using averaged Gaussian perplexities.
  
  In contrast to :class:`MultiscaleMixture`, which uses a Gaussian mixture
  kernel, here, we first compute single scale Gaussian kernels, convert them
  to probability distributions, then average them out between scales.
  
  Please see the :ref:`parameter-guide` for more information.
  
  Parameters
  ----------
  data: np.ndarray
      The data matrix.
  
  perplexities: List[float]
      A list of perplexity values, which will be used in the multiscale
      Gaussian kernel. Perplexity can be thought of as the continuous
      :math:`k` number of nearest neighbors, for which t-SNE will attempt to
      preserve distances.
  
  method: str
      Specifies the nearest neighbor method to use. Can be ``exact``, ``annoy``,
      ``pynndescent``, ``hnsw``, ``approx``, or ``auto`` (default). ``approx``
      uses Annoy if the input data matrix is not a sparse object and if Annoy
      supports the given metric. Otherwise, it uses Pynndescent. ``auto`` uses
      exact nearest neighbors for N<1000 and the same heuristic as ``approx``
      for N>=1000.
  
  metric: Union[str, Callable]
      The metric to be used to compute affinities between points in the
      original space.
  
  metric_params: dict
      Additional keyword arguments for the metric function.
  
  symmetrize: bool
      Symmetrize the affinity matrix. During standard t-SNE optimization, the
      affinities are symmetrized. However, when embedding new data points into
      existing embeddings, symmetrization is not performed.
  
  n_jobs: int
      The number of threads to use while running t-SNE. This follows the
      scikit-learn convention, ``-1`` meaning all processors, ``-2`` meaning
      all but one, etc.
  
  random_state: Union[int, RandomState]
      If the value is an int, random_state is the seed used by the random
      number generator. If the value is a RandomState instance, then it will
      be used as the random number generator. If the value is None, the random
      number generator is the RandomState instance used by `np.random`.
  
  verbose: bool
  
  knn_index: Optional[nearest_neighbors.KNNIndex]
      Optionally, a precomptued ``openTSNE.nearest_neighbors.KNNIndex`` object
      can be specified. This option will ignore any KNN-related parameters.
      When ``knn_index`` is specified, ``data`` must be set to None.
class_docstr_tok: ["Calculate","affinities","using","averaged","Gaussian","perplexities",".","In","contrast","to",":","class",":","`","MultiscaleMixture","`",",","which","uses","a","Gaussian","mixture","kernel",",","here",",","we","first","compute","single","scale","Gaussian","kernels",",","convert","them","to","probability","distributions",",","then","average","them","out","between","scales",".","Please","see","the",":","ref",":","`","parameter-guide","`","for","more","information",".","Parameters","--","--","--","--","--","data",":","np.ndarray","The","data","matrix",".","perplexities",":","List","[","float","]","A","list","of","perplexity","values",",","which","will","be","used","in","the","multiscale","Gaussian","kernel",".","Perplexity","can","be","thought","of","as","the","continuous",":","math",":","`","k","`","number","of","nearest","neighbors",",","for","which","t-SNE","will","attempt","to","preserve","distances",".","method",":","str","Specifies","the","nearest","neighbor","method","to","use",".","Can","be","``","exact","``",",","``","annoy","``",",","``","pynndescent","``",",","``","hnsw","``",",","``","approx","``",",","or","``","auto","``","(","default",")",".","``","approx","``","uses","Annoy","if","the","input","data","matrix","is","not","a","sparse","object","and","if","Annoy","supports","the","given","metric",".","Otherwise",",","it","uses","Pynndescent",".","``","auto","``","uses","exact","nearest","neighbors","for","N","<","1000","and","the","same","heuristic","as","``","approx","``","for","N",">","=1000",".","metric",":","Union","[","str",",","Callable","]","The","metric","to","be","used","to","compute","affinities","between","points","in","the","original","space",".","metric_params",":","dict","Additional","keyword","arguments","for","the","metric","function",".","symmetrize",":","bool","Symmetrize","the","affinity","matrix",".","During","standard","t-SNE","optimization",",","the","affinities","are","symmetrized",".","However",",","when","embedding","new","data","points","into","existing","embeddings",",","symmetrization","is","not","performed",".","n_jobs",":","int","The","number","of","threads","to","use","while","running","t-SNE",".","This","follows","the","scikit-learn","convention",",","``","-1","``","meaning","all","processors",",","``","-2","``","meaning","all","but","one",",","etc",".","random_state",":","Union","[","int",",","RandomState","]","If","the","value","is","an","int",",","random_state","is","the","seed","used","by","the","random","number","generator",".","If","the","value","is","a","RandomState","instance",",","then","it","will","be","used","as","the","random","number","generator",".","If","the","value","is","None",",","the","random","number","generator","is","the","RandomState","instance","used","by","`","np.random","`",".","verbose",":","bool","knn_index",":","Optional","[","nearest_neighbors.KNNIndex","]","Optionally",",","a","precomptued","``","openTSNE.nearest_neighbors.KNNIndex","``","object","can","be","specified",".","This","option","will","ignore","any","KNN-related","parameters",".","When","``","knn_index","``","is","specified",",","``","data","``","must","be","set","to","None","."]
code: def _calculate_P(
      neighbors,
      distances,
      perplexities,
      symmetrize=True,
      normalization="pair-wise",
      n_reference_samples=None,
      n_jobs=1,
  ):
      # Compute normalized probabilities for each perplexity
      partial_Ps = [
          joint_probabilities_nn(
              neighbors,
              distances,
              [perplexity],
              symmetrize=symmetrize,
              normalization=normalization,
              n_reference_samples=n_reference_samples,
              n_jobs=n_jobs,
          )
          for perplexity in perplexities
      ]
      # Sum them together, then normalize
      P = reduce(operator.add, partial_Ps, 0)
  
      # Take care to properly normalize the affinity matrix
      if normalization == "pair-wise":
          P /= np.sum(P)
      elif normalization == "point-wise":
          P = sp.diags(np.asarray(1 / P.sum(axis=1)).ravel()) @ P
  
      return P
  
imports: import logging
  import numbers
  import operator
  from functools import reduce
  import numpy
  import scipy.sparse
  from openTSNE import _tsne
  from openTSNE import nearest_neighbors
  from openTSNE import utils
  from openTSNE.utils import is_package_installed
  import warnings
label_desc: Use image node_id 1 for calling the Multiscale obj's underlying member method code with example usage: obj._calculate_P(neighbors, distances, perplexities, symmetrize, normalization, n_reference_samples, n_jobs) and returns: P