class_docstr: Processes the graph via Graph Diffusion Convolution (GDC) from the
  `"Diffusion Improves Graph Learning" <https://www.kdd.in.tum.de/gdc>`_
  paper (functional name: :obj:`gdc`).
  
  .. note::
  
      The paper offers additional advice on how to choose the
      hyperparameters.
      For an example of using GCN with GDC, see `examples/gcn.py
      <https://github.com/pyg-team/pytorch_geometric/blob/master/examples/
      gcn.py>`_.
  
  Args:
      self_loop_weight (float, optional): Weight of the added self-loop.
          Set to :obj:`None` to add no self-loops. (default: :obj:`1`)
      normalization_in (str, optional): Normalization of the transition
          matrix on the original (input) graph. Possible values:
          :obj:`"sym"`, :obj:`"col"`, and :obj:`"row"`.
          See :func:`GDC.transition_matrix` for details.
          (default: :obj:`"sym"`)
      normalization_out (str, optional): Normalization of the transition
          matrix on the transformed GDC (output) graph. Possible values:
          :obj:`"sym"`, :obj:`"col"`, :obj:`"row"`, and :obj:`None`.
          See :func:`GDC.transition_matrix` for details.
          (default: :obj:`"col"`)
      diffusion_kwargs (dict, optional): Dictionary containing the parameters
          for diffusion.
          `method` specifies the diffusion method (:obj:`"ppr"`,
          :obj:`"heat"` or :obj:`"coeff"`).
          Each diffusion method requires different additional parameters.
          See :func:`GDC.diffusion_matrix_exact` or
          :func:`GDC.diffusion_matrix_approx` for details.
          (default: :obj:`dict(method='ppr', alpha=0.15)`)
      sparsification_kwargs (dict, optional): Dictionary containing the
          parameters for sparsification.
          `method` specifies the sparsification method (:obj:`"threshold"` or
          :obj:`"topk"`).
          Each sparsification method requires different additional
          parameters.
          See :func:`GDC.sparsify_dense` for details.
          (default: :obj:`dict(method='threshold', avg_degree=64)`)
      exact (bool, optional): Whether to exactly calculate the diffusion
          matrix.
          Note that the exact variants are not scalable.
          They densify the adjacency matrix and calculate either its inverse
          or its matrix exponential.
          However, the approximate variants do not support edge weights and
          currently only personalized PageRank and sparsification by
          threshold are implemented as fast, approximate versions.
          (default: :obj:`True`)
  
  :rtype: :class:`torch_geometric.data.Data`
class_docstr_tok: ["Processes","the","graph","via","Graph","Diffusion","Convolution","(","GDC",")","from","the","`","``","Diffusion","Improves","Graph","Learning","''","<","https",":","\/\/www.kdd.in.tum.de\/gdc",">","`","_","paper","(","functional","name",":",":","obj",":","`","gdc","`",")",".","..","note",":",":","The","paper","offers","additional","advice","on","how","to","choose","the","hyperparameters",".","For","an","example","of","using","GCN","with","GDC",",","see","`","examples\/gcn.py","<","https",":","\/\/github.com\/pyg-team\/pytorch_geometric\/blob\/master\/examples\/","gcn.py",">","`","_",".","Args",":","self_loop_weight","(","float",",","optional",")",":","Weight","of","the","added","self-loop",".","Set","to",":","obj",":","`","None","`","to","add","no","self-loops",".","(","default",":",":","obj",":","`","1","`",")","normalization_in","(","str",",","optional",")",":","Normalization","of","the","transition","matrix","on","the","original","(","input",")","graph",".","Possible","values",":",":","obj",":","`","``","sym","''","`",",",":","obj",":","`","``","col","''","`",",","and",":","obj",":","`","``","row","''","`",".","See",":","func",":","`","GDC.transition_matrix","`","for","details",".","(","default",":",":","obj",":","`","``","sym","''","`",")","normalization_out","(","str",",","optional",")",":","Normalization","of","the","transition","matrix","on","the","transformed","GDC","(","output",")","graph",".","Possible","values",":",":","obj",":","`","``","sym","''","`",",",":","obj",":","`","``","col","''","`",",",":","obj",":","`","``","row","''","`",",","and",":","obj",":","`","None","`",".","See",":","func",":","`","GDC.transition_matrix","`","for","details",".","(","default",":",":","obj",":","`","``","col","''","`",")","diffusion_kwargs","(","dict",",","optional",")",":","Dictionary","containing","the","parameters","for","diffusion",".","`","method","`","specifies","the","diffusion","method","(",":","obj",":","`","``","ppr","''","`",",",":","obj",":","`","``","heat","''","`","or",":","obj",":","`","``","coeff","''","`",")",".","Each","diffusion","method","requires","different","additional","parameters",".","See",":","func",":","`","GDC.diffusion_matrix_exact","`","or",":","func",":","`","GDC.diffusion_matrix_approx","`","for","details",".","(","default",":",":","obj",":","`","dict","(","method='ppr","'",",","alpha=0.15",")","`",")","sparsification_kwargs","(","dict",",","optional",")",":","Dictionary","containing","the","parameters","for","sparsification",".","`","method","`","specifies","the","sparsification","method","(",":","obj",":","`","``","threshold","''","`","or",":","obj",":","`","``","topk","''","`",")",".","Each","sparsification","method","requires","different","additional","parameters",".","See",":","func",":","`","GDC.sparsify_dense","`","for","details",".","(","default",":",":","obj",":","`","dict","(","method='threshold","'",",","avg_degree=64",")","`",")","exact","(","bool",",","optional",")",":","Whether","to","exactly","calculate","the","diffusion","matrix",".","Note","that","the","exact","variants","are","not","scalable",".","They","densify","the","adjacency","matrix","and","calculate","either","its","inverse","or","its","matrix","exponential",".","However",",","the","approximate","variants","do","not","support","edge","weights","and","currently","only","personalized","PageRank","and","sparsification","by","threshold","are","implemented","as","fast",",","approximate","versions",".","(","default",":",":","obj",":","`","True","`",")",":","rtype",":",":","class",":","`","torch_geometric.data.Data","`"]
docstr: Sparsifies the given dense matrix.
  
  Args:
      matrix (Tensor): Matrix to sparsify.
      method (str): Method of sparsification. Options:
  
          1. :obj:`"threshold"`: Remove all edges with weights smaller
             than :obj:`eps`.
             Additionally expects one of these parameters:
  
             - **eps** (*float*) - Threshold to bound edges at.
  
             - **avg_degree** (*int*) - If :obj:`eps` is not given,
               it can optionally be calculated by calculating the
               :obj:`eps` required to achieve a given :obj:`avg_degree`.
  
          2. :obj:`"topk"`: Keep edges with top :obj:`k` edge weights per
             node (column).
             Additionally expects the following parameters:
  
             - **k** (*int*) - Specifies the number of edges to keep.
  
             - **dim** (*int*) - The axis along which to take the top
               :obj:`k`.
  
  :rtype: (:class:`LongTensor`, :class:`Tensor`)
docstr_tok: ["Sparsifies","the","given","dense","matrix",".","Args",":","matrix","(","Tensor",")",":","Matrix","to","sparsify",".","method","(","str",")",":","Method","of","sparsification",".","Options",":","1.",":","obj",":","`","``","threshold","''","`",":","Remove","all","edges","with","weights","smaller","than",":","obj",":","`","eps","`",".","Additionally","expects","one","of","these","parameters",":","-","*","*","eps","*","*","(","*","float","*",")","-","Threshold","to","bound","edges","at",".","-","*","*","avg_degree","*","*","(","*","int","*",")","-","If",":","obj",":","`","eps","`","is","not","given",",","it","can","optionally","be","calculated","by","calculating","the",":","obj",":","`","eps","`","required","to","achieve","a","given",":","obj",":","`","avg_degree","`",".","2.",":","obj",":","`","``","topk","''","`",":","Keep","edges","with","top",":","obj",":","`","k","`","edge","weights","per","node","(","column",")",".","Additionally","expects","the","following","parameters",":","-","*","*","k","*","*","(","*","int","*",")","-","Specifies","the","number","of","edges","to","keep",".","-","*","*","dim","*","*","(","*","int","*",")","-","The","axis","along","which","to","take","the","top",":","obj",":","`","k","`",".",":","rtype",":","(",":","class",":","`","LongTensor","`",",",":","class",":","`","Tensor","`",")"]
code: def sparsify_dense(  # noqa: D417
      self,
      matrix: Tensor,
      method: str,
      **kwargs: Any,
  ) -> Tuple[Tensor, Tensor]:
      r"""Sparsifies the given dense matrix.
  
      Args:
          matrix (Tensor): Matrix to sparsify.
          method (str): Method of sparsification. Options:
  
              1. :obj:`"threshold"`: Remove all edges with weights smaller
                 than :obj:`eps`.
                 Additionally expects one of these parameters:
  
                 - **eps** (*float*) - Threshold to bound edges at.
  
                 - **avg_degree** (*int*) - If :obj:`eps` is not given,
                   it can optionally be calculated by calculating the
                   :obj:`eps` required to achieve a given :obj:`avg_degree`.
  
              2. :obj:`"topk"`: Keep edges with top :obj:`k` edge weights per
                 node (column).
                 Additionally expects the following parameters:
  
                 - **k** (*int*) - Specifies the number of edges to keep.
  
                 - **dim** (*int*) - The axis along which to take the top
                   :obj:`k`.
  
      :rtype: (:class:`LongTensor`, :class:`Tensor`)
      """
      assert matrix.shape[0] == matrix.shape[1]
      N = matrix.shape[1]
  
      if method == "threshold":
          if "eps" not in kwargs.keys():
              kwargs["eps"] = self.__calculate_eps__(
                  matrix, N, kwargs["avg_degree"]
              )
  
          edge_index = (
              (matrix >= kwargs["eps"]).nonzero(as_tuple=False).t()
          )
          edge_index_flat = edge_index[0] * N + edge_index[1]
          edge_weight = matrix.flatten()[edge_index_flat]
  
      elif method == "topk":
          k, dim = min(N, kwargs["k"]), kwargs["dim"]
          assert dim in [0, 1]
          sort_idx = torch.argsort(matrix, dim=dim, descending=True)
          if dim == 0:
              top_idx = sort_idx[:k]
              edge_weight = torch.gather(
                  matrix, dim=dim, index=top_idx
              ).flatten()
  
              row_idx = torch.arange(0, N, device=matrix.device).repeat(
                  k
              )
              edge_index = torch.stack(
                  [top_idx.flatten(), row_idx], dim=0
              )
          else:
              top_idx = sort_idx[:, :k]
              edge_weight = torch.gather(
                  matrix, dim=dim, index=top_idx
              ).flatten()
  
              col_idx = torch.arange(
                  0, N, device=matrix.device
              ).repeat_interleave(k)
              edge_index = torch.stack(
                  [col_idx, top_idx.flatten()], dim=0
              )
      else:
          raise ValueError(f"GDC sparsification '{method}' unknown")
  
      return edge_index, edge_weight
  
imports: from typing import Any, Dict, Tuple
  import numpy
  import torch
  from scipy.linalg import expm
  from torch import Tensor
  from torch_geometric.data import Data
  from torch_geometric.data.datapipes import functional_transform
  from torch_geometric.transforms import BaseTransform
  from torch_geometric.utils import add_self_loops, coalesce, get_ppr, is_undirected, scatter, sort_edge_index, to_dense_adj
label_desc: Use image node_id 6 for calling the GDC obj's underlying member method code with example usage: obj.sparsify_dense(matrix, method) and returns: edge_index,  edge_weight