U
    ª9%eo­  ã                   @   sÈ  d Z ddlZddlZddlmZ ddlZddlmZ ddl	m
Z
mZmZmZ ddlmZ dd	d
ddddddddddddddddgZedƒd3dd„ƒZedƒd4dd	„ƒZeZeZedƒd5dd
„ƒZedƒd6d d„ƒZed!ƒd7d"d„ƒZed!ƒd8d#d„ƒZed$ƒd9d&d„ƒZedƒd:d'd„ƒZd(d)„ Zedƒd;d*d„ƒZed$ƒd<d+d„ƒZed$ƒd=d,d„ƒZed!ƒd>d-d„ƒZed!ƒd?d.d„ƒZ edƒd@d/d„ƒZ!edƒdAd0d„ƒZ"edƒdBd1d„ƒZ#ed!ƒdCd2d„ƒZ$dS )Dz 
Generators for random graphs.

é    N)Údefaultdict)Úpy_random_stateé   )Úcomplete_graphÚempty_graphÚ
path_graphÚ
star_graph)Údegree_sequence_treeÚfast_gnp_random_graphÚgnp_random_graphÚdense_gnm_random_graphÚgnm_random_graphÚerdos_renyi_graphÚbinomial_graphÚnewman_watts_strogatz_graphÚwatts_strogatz_graphÚconnected_watts_strogatz_graphÚrandom_regular_graphÚbarabasi_albert_graphÚdual_barabasi_albert_graphÚextended_barabasi_albert_graphÚpowerlaw_cluster_graphÚrandom_lobsterÚrandom_shell_graphÚrandom_powerlaw_treeÚrandom_powerlaw_tree_sequenceÚrandom_kernel_graphé   Fc           	      C   s,  t | ƒ}|dks|dkr*tj| |||dS t d| ¡}|r´t |¡}d}d}|| k r´t d| ¡  ¡}|d t|| ƒ }||krž|| k rž|| }|d }q||| k rN| ||¡ qNd}d}|| k r(t d| ¡  ¡}|d t|| ƒ }||kr|| k r|| }|d }qì|| k r¼| ||¡ q¼|S )u€  Returns a $G_{n,p}$ random graph, also known as an ErdÅ‘s-RÃ©nyi graph or
    a binomial graph.

    Parameters
    ----------
    n : int
        The number of nodes.
    p : float
        Probability for edge creation.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True, this function returns a directed graph.

    Notes
    -----
    The $G_{n,p}$ graph algorithm chooses each of the $[n (n - 1)] / 2$
    (undirected) or $n (n - 1)$ (directed) possible edges with probability $p$.

    This algorithm [1]_ runs in $O(n + m)$ time, where `m` is the expected number of
    edges, which equals $p n (n - 1) / 2$. This should be faster than
    :func:`gnp_random_graph` when $p$ is small and the expected number of edges
    is small (that is, the graph is sparse).

    See Also
    --------
    gnp_random_graph

    References
    ----------
    .. [1] Vladimir Batagelj and Ulrik Brandes,
       "Efficient generation of large random networks",
       Phys. Rev. E, 71, 036113, 2005.
    r   r   )ÚseedÚdirectedg      ð?éÿÿÿÿ)	r   Únxr   ÚmathÚlogÚDiGraphÚrandomÚintÚadd_edge)	ÚnÚpr   r   ÚGZlpÚvÚwÚlr© r.   ú`/var/www/html/Darija-Ai-API/env/lib/python3.8/site-packages/networkx/generators/random_graphs.pyr
   '   s6    %



c                 C   sˆ   |rt  t| ƒd¡}t ¡ }nt  t| ƒd¡}t ¡ }| t| ƒ¡ |dkrP|S |dkrdt| |dS |D ]}| 	¡ |k rh|j
|Ž  qh|S )u³  Returns a $G_{n,p}$ random graph, also known as an ErdÅ‘s-RÃ©nyi graph
    or a binomial graph.

    The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

    Parameters
    ----------
    n : int
        The number of nodes.
    p : float
        Probability for edge creation.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True, this function returns a directed graph.

    See Also
    --------
    fast_gnp_random_graph

    Notes
    -----
    This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
    small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

    :func:`binomial_graph` and :func:`erdos_renyi_graph` are
    aliases for :func:`gnp_random_graph`.

    >>> nx.binomial_graph is nx.gnp_random_graph
    True
    >>> nx.erdos_renyi_graph is nx.gnp_random_graph
    True

    References
    ----------
    .. [1] P. ErdÅ‘s and A. RÃ©nyi, On Random Graphs, Publ. Math. 6, 290 (1959).
    .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).
    r   r   r   ©Zcreate_using)Ú	itertoolsÚpermutationsÚranger!   r$   ÚcombinationsÚGraphÚadd_nodes_fromr   r%   r'   )r(   r)   r   r   Úedgesr*   Úer.   r.   r/   r   n   s    )
c           	      C   s²   | | d  d }||kr"t | ƒ}nt| ƒ}| dks:||kr>|S d}d}d}d}| || ¡|| k r„| ||¡ |d7 }||kr„|S |d7 }|d7 }|| krN|d7 }|d }qNdS )a†  Returns a $G_{n,m}$ random graph.

    In the $G_{n,m}$ model, a graph is chosen uniformly at random from the set
    of all graphs with $n$ nodes and $m$ edges.

    This algorithm should be faster than :func:`gnm_random_graph` for dense
    graphs.

    Parameters
    ----------
    n : int
        The number of nodes.
    m : int
        The number of edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    See Also
    --------
    gnm_random_graph

    Notes
    -----
    Algorithm by Keith M. Briggs Mar 31, 2006.
    Inspired by Knuth's Algorithm S (Selection sampling technique),
    in section 3.4.2 of [1]_.

    References
    ----------
    .. [1] Donald E. Knuth, The Art of Computer Programming,
        Volume 2/Seminumerical algorithms, Third Edition, Addison-Wesley, 1997.
    r   r   r   N)r   r   Ú	randranger'   )	r(   Úmr   Zmmaxr*   Úur+   ÚtÚkr.   r.   r/   r   ®   s(    #
c           
      C   s¶   |rt  ¡ }nt  ¡ }| t| ƒ¡ | dkr0|S | | d  }|sH|d }||kr\t| |dS t|ƒ}d}||k r²| |¡}| |¡}	||	ksh| ||	¡rœqhqh| 	||	¡ |d }qh|S )a˜  Returns a $G_{n,m}$ random graph.

    In the $G_{n,m}$ model, a graph is chosen uniformly at random from the set
    of all graphs with $n$ nodes and $m$ edges.

    This algorithm should be faster than :func:`dense_gnm_random_graph` for
    sparse graphs.

    Parameters
    ----------
    n : int
        The number of nodes.
    m : int
        The number of edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True return a directed graph

    See also
    --------
    dense_gnm_random_graph

    r   g       @r0   r   )
r!   r$   r5   r6   r3   r   ÚlistÚchoiceÚhas_edger'   )
r(   r:   r   r   r*   Z	max_edgesÚnlistÚ
edge_countr;   r+   r.   r.   r/   r   ë   s*    



é   c                 C   s  || krt  d¡‚|| kr$t  | ¡S t| ƒ}t| ¡ ƒ}|}td|d d ƒD ]B}||d… |d|…  }tt|ƒƒD ]}	| ||	 ||	 ¡ qvqNt| 	¡ ƒ}
|
D ]^\}}| 
¡ |k r¢| |¡}||ksÔ| ||¡rô| |¡}| |¡| d krÀq¢qÀ| ||¡ q¢|S )uØ  Returns a Newmanâ€“Wattsâ€“Strogatz small-world graph.

    Parameters
    ----------
    n : int
        The number of nodes.
    k : int
        Each node is joined with its `k` nearest neighbors in a ring
        topology.
    p : float
        The probability of adding a new edge for each edge.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Notes
    -----
    First create a ring over $n$ nodes [1]_.  Then each node in the ring is
    connected with its $k$ nearest neighbors (or $k - 1$ neighbors if $k$
    is odd).  Then shortcuts are created by adding new edges as follows: for
    each edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest
    neighbors" with probability $p$ add a new edge $(u, w)$ with
    randomly-chosen existing node $w$.  In contrast with
    :func:`watts_strogatz_graph`, no edges are removed.

    See Also
    --------
    watts_strogatz_graph

    References
    ----------
    .. [1] M. E. J. Newman and D. J. Watts,
       Renormalization group analysis of the small-world network model,
       Physics Letters A, 263, 341, 1999.
       https://doi.org/10.1016/S0375-9601(99)00757-4
    z"k>=n, choose smaller k or larger nr   r   Nr   )r!   ÚNetworkXErrorr   r   r>   Únodesr3   Úlenr'   r7   r%   r?   r@   Údegree)r(   r=   r)   r   r*   rA   ZfromvÚjZtovÚir8   r;   r+   r,   r.   r.   r/   r   "  s*    &



c                 C   s$  || krt  d¡‚|| kr$t  | ¡S t  ¡ }tt| ƒƒ}td|d d ƒD ],}||d… |d|…  }| t||ƒ¡ qJtd|d d ƒD ]”}||d… |d|…  }t||ƒD ]l\}}	| ¡ |k r°| 	|¡}
|
|ksä| 
||
¡r| 	|¡}
| |¡| d krÎq°qÎ| ||	¡ | ||
¡ q°qŠ|S )uQ  Returns a Wattsâ€“Strogatz small-world graph.

    Parameters
    ----------
    n : int
        The number of nodes
    k : int
        Each node is joined with its `k` nearest neighbors in a ring
        topology.
    p : float
        The probability of rewiring each edge
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    See Also
    --------
    newman_watts_strogatz_graph
    connected_watts_strogatz_graph

    Notes
    -----
    First create a ring over $n$ nodes [1]_.  Then each node in the ring is joined
    to its $k$ nearest neighbors (or $k - 1$ neighbors if $k$ is odd).
    Then shortcuts are created by replacing some edges as follows: for each
    edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest neighbors"
    with probability $p$ replace it with a new edge $(u, w)$ with uniformly
    random choice of existing node $w$.

    In contrast with :func:`newman_watts_strogatz_graph`, the random rewiring
    does not increase the number of edges. The rewired graph is not guaranteed
    to be connected as in :func:`connected_watts_strogatz_graph`.

    References
    ----------
    .. [1] Duncan J. Watts and Steven H. Strogatz,
       Collective dynamics of small-world networks,
       Nature, 393, pp. 440--442, 1998.
    z!k>n, choose smaller k or larger nr   r   Nr   )r!   rD   r   r5   r>   r3   Úadd_edges_fromÚzipr%   r?   r@   rG   Úremove_edger'   )r(   r=   r)   r   r*   rE   rH   Útargetsr;   r+   r,   r.   r.   r/   r   h  s*    )



é   éd   c                 C   s<   t |ƒD ]$}t| |||ƒ}t |¡r|  S qt d¡‚dS )u¶  Returns a connected Wattsâ€“Strogatz small-world graph.

    Attempts to generate a connected graph by repeated generation of
    Wattsâ€“Strogatz small-world graphs.  An exception is raised if the maximum
    number of tries is exceeded.

    Parameters
    ----------
    n : int
        The number of nodes
    k : int
        Each node is joined with its `k` nearest neighbors in a ring
        topology.
    p : float
        The probability of rewiring each edge
    tries : int
        Number of attempts to generate a connected graph.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Notes
    -----
    First create a ring over $n$ nodes [1]_.  Then each node in the ring is joined
    to its $k$ nearest neighbors (or $k - 1$ neighbors if $k$ is odd).
    Then shortcuts are created by replacing some edges as follows: for each
    edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest neighbors"
    with probability $p$ replace it with a new edge $(u, w)$ with uniformly
    random choice of existing node $w$.
    The entire process is repeated until a connected graph results.

    See Also
    --------
    newman_watts_strogatz_graph
    watts_strogatz_graph

    References
    ----------
    .. [1] Duncan J. Watts and Steven H. Strogatz,
       Collective dynamics of small-world networks,
       Nature, 393, pp. 440--442, 1998.
    z Maximum number of tries exceededN)r3   r   r!   Zis_connectedrD   )r(   r=   r)   Útriesr   rI   r*   r.   r.   r/   r   ²  s
    ,

c                    s   ˆˆ d dkrt  d¡‚dˆ  kr.ˆk s:n t  d¡‚ˆdkrJtˆƒS dd„ ‰ ‡ ‡‡‡fdd„}|ƒ }|d	krz|ƒ }qjt  ¡ }| |¡ |S )
a@  Returns a random $d$-regular graph on $n$ nodes.

    A regular graph is a graph where each node has the same number of neighbors.

    The resulting graph has no self-loops or parallel edges.

    Parameters
    ----------
    d : int
      The degree of each node.
    n : integer
      The number of nodes. The value of $n \times d$ must be even.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Notes
    -----
    The nodes are numbered from $0$ to $n - 1$.

    Kim and Vu's paper [2]_ shows that this algorithm samples in an
    asymptotically uniform way from the space of random graphs when
    $d = O(n^{1 / 3 - \epsilon})$.

    Raises
    ------

    NetworkXError
        If $n \times d$ is odd or $d$ is greater than or equal to $n$.

    References
    ----------
    .. [1] A. Steger and N. Wormald,
       Generating random regular graphs quickly,
       Probability and Computing 8 (1999), 377-396, 1999.
       https://doi.org/10.1017/S0963548399003867

    .. [2] Jeong Han Kim and Van H. Vu,
       Generating random regular graphs,
       Proceedings of the thirty-fifth ACM symposium on Theory of computing,
       San Diego, CA, USA, pp 213--222, 2003.
       http://portal.acm.org/citation.cfm?id=780542.780576
    r   r   zn * d must be evenz+the 0 <= d < n inequality must be satisfiedc                 S   sR   |sdS |D ]@}|D ]6}||kr$ q||kr6|| }}||f| kr  dS qqdS )NTFr.   )r7   Úpotential_edgesÚs1Ús2r.   r.   r/   Ú	_suitable  s    
z'random_regular_graph.<locals>._suitablec                     sÈ   t ƒ } ttˆƒƒˆ }|rÄtdd„ ƒ}ˆ |¡ t|ƒ}t||ƒD ]^\}}||kr\|| }}||kr€||f| kr€|  ||f¡ qB||  d7  < ||  d7  < qBˆ | |ƒs°d S dd„ | ¡ D ƒ}q| S )Nc                   S   s   dS )Nr   r.   r.   r.   r.   r/   Ú<lambda>6  ó    z=random_regular_graph.<locals>._try_creation.<locals>.<lambda>r   c                 S   s"   g | ]\}}t |ƒD ]}|‘qqS r.   ©r3   )Ú.0ÚnodeZ	potentialÚ_r.   r.   r/   Ú
<listcomp>E  s   
 þz?random_regular_graph.<locals>._try_creation.<locals>.<listcomp>)	Úsetr>   r3   r   ÚshuffleÚiterrK   ÚaddÚitems)r7   ZstubsrQ   ZstubiterrR   rS   ©rT   Údr(   r   r.   r/   Ú_try_creation/  s&    


þz+random_regular_graph.<locals>._try_creationN)r!   rD   r   r5   rJ   )rb   r(   r   rc   r7   r*   r.   ra   r/   r   æ  s    -

 
c                 C   s,   t ƒ }t|ƒ|k r(| | ¡}| |¡ q|S )zÛReturn m unique elements from seq.

    This differs from random.sample which can return repeated
    elements if seq holds repeated elements.

    Note: rng is a random.Random or numpy.random.RandomState instance.
    )r\   rF   r?   r_   )Úseqr:   ÚrngrM   Úxr.   r.   r/   Ú_random_subsetY  s
    
rg   c                 C   sÜ   |dk s|| kr&t  d|› d| › ¡‚|dkr8t|ƒ}n8t|ƒ|k sPt|ƒ| krht  d|› d| › d¡‚| ¡ }dd	„ | ¡ D ƒ}t|ƒ}|| k rØt|||ƒ}| t|g| |ƒ¡ | 	|¡ | 	|g| ¡ |d7 }qŠ|S )
u|  Returns a random graph using BarabÃ¡siâ€“Albert preferential attachment

    A graph of $n$ nodes is grown by attaching new nodes each with $m$
    edges that are preferentially attached to existing nodes with high degree.

    Parameters
    ----------
    n : int
        Number of nodes
    m : int
        Number of edges to attach from a new node to existing nodes
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    initial_graph : Graph or None (default)
        Initial network for BarabÃ¡siâ€“Albert algorithm.
        It should be a connected graph for most use cases.
        A copy of `initial_graph` is used.
        If None, starts from a star graph on (m+1) nodes.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `m` does not satisfy ``1 <= m < n``, or
        the initial graph number of nodes m0 does not satisfy ``m <= m0 <= n``.

    References
    ----------
    .. [1] A. L. BarabÃ¡si and R. Albert "Emergence of scaling in
       random networks", Science 286, pp 509-512, 1999.
    r   u;   BarabÃ¡siâ€“Albert network must have m >= 1 and m < n, m = ú, n = Nu1   BarabÃ¡siâ€“Albert initial graph needs between m=z and n=ú nodesc                 S   s"   g | ]\}}t |ƒD ]}|‘qqS r.   rW   ©rX   r(   rb   rZ   r.   r.   r/   r[   ž  s     
  z)barabasi_albert_graph.<locals>.<listcomp>)
r!   rD   r   rF   ÚcopyrG   rg   rJ   rK   Úextend)r(   r:   r   Úinitial_graphr*   Úrepeated_nodesÚsourcerM   r.   r.   r/   r   h  s(    &ÿ
ÿ

c                 C   s€  |dk s|| kr&t  d|› d| › ¡‚|dk s6|| krLt  d|› d| › ¡‚|dk s\|dkrlt  d|› ¡‚|dkr€t| ||ƒS |dkr”t| ||ƒS |dkr¬tt||ƒƒ}nDt|ƒt||ƒk sÊt|ƒ| krèt  dt||ƒ› d	| › d
¡‚| ¡ }t|ƒ}dd„ | ¡ D ƒ}t|ƒ}	|	| k r|| 	¡ |k r0|}
n|}
t
||
|ƒ}| t|	g|
 |ƒ¡ | |¡ | |	g|
 ¡ |	d7 }	q|S )u¯  Returns a random graph using dual BarabÃ¡siâ€“Albert preferential attachment

    A graph of $n$ nodes is grown by attaching new nodes each with either $m_1$
    edges (with probability $p$) or $m_2$ edges (with probability $1-p$) that
    are preferentially attached to existing nodes with high degree.

    Parameters
    ----------
    n : int
        Number of nodes
    m1 : int
        Number of edges to link each new node to existing nodes with probability $p$
    m2 : int
        Number of edges to link each new node to existing nodes with probability $1-p$
    p : float
        The probability of attaching $m_1$ edges (as opposed to $m_2$ edges)
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    initial_graph : Graph or None (default)
        Initial network for BarabÃ¡siâ€“Albert algorithm.
        A copy of `initial_graph` is used.
        It should be connected for most use cases.
        If None, starts from an star graph on max(m1, m2) + 1 nodes.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `m1` and `m2` do not satisfy ``1 <= m1,m2 < n``, or
        `p` does not satisfy ``0 <= p <= 1``, or
        the initial graph number of nodes m0 does not satisfy m1, m2 <= m0 <= n.

    References
    ----------
    .. [1] N. Moshiri "The dual-Barabasi-Albert model", arXiv:1810.10538.
    r   u;   Dual BarabÃ¡siâ€“Albert must have m1 >= 1 and m1 < n, m1 = rh   u;   Dual BarabÃ¡siâ€“Albert must have m2 >= 1 and m2 < n, m2 = r   u;   Dual BarabÃ¡siâ€“Albert network must have 0 <= p <= 1, p = NuA   BarabÃ¡siâ€“Albert initial graph must have between max(m1, m2) = z	 and n = ri   c                 S   s"   g | ]\}}t |ƒD ]}|‘qqS r.   rW   rj   r.   r.   r/   r[   ü  s     
  z.dual_barabasi_albert_graph.<locals>.<listcomp>)r!   rD   r   r   ÚmaxrF   rk   r>   rG   r%   rg   rJ   rK   rl   )r(   Úm1Úm2r)   r   rm   r*   rM   rn   ro   r:   r.   r.   r/   r   °  sH    +ÿÿÿÿ

c                    sú  |dk s|| kr*d|› d| › }t  |¡‚|| dkrPd|› d|› }t  |¡‚t|ƒ}g }| t|ƒ¡ |}|| k rö| ¡ }	t|ƒd ‰ t|ƒˆ  d }
|	|k rp| ¡ |
| krp‡ fdd„| ¡ D ƒ}t|ƒD ]–}| 	|¡}t
|| ƒ‰ˆ |¡ | 	‡fd	d„|D ƒ¡}| ||¡ | |¡ | |¡ | |¡ˆ krL| |¡ | |¡ˆ krÖ||krÖ| |¡ qÖqn||	  krŒ|| k r¬n n|| ¡   kr®|
k r¬n nú‡ fd
d„| ¡ D ƒ}t|ƒD ]Ø}| 	|¡}t
|| ƒ‰| 	ˆ¡}ˆ |¡ | 	‡fdd„|D ƒ¡}| ||¡ | ||¡ | |¡ | |¡ | |¡dkrf||krf| |¡ ||krŒ| |¡ˆ kr¦| |¡ n| |¡dkrÐ| |¡ qÐqnt|||ƒ}| t|g| |ƒ¡ | |¡ | |g|d  ¡ |d7 }qn|S )uˆ  Returns an extended BarabÃ¡siâ€“Albert model graph.

    An extended BarabÃ¡siâ€“Albert model graph is a random graph constructed
    using preferential attachment. The extended model allows new edges,
    rewired edges or new nodes. Based on the probabilities $p$ and $q$
    with $p + q < 1$, the growing behavior of the graph is determined as:

    1) With $p$ probability, $m$ new edges are added to the graph,
    starting from randomly chosen existing nodes and attached preferentially at the other end.

    2) With $q$ probability, $m$ existing edges are rewired
    by randomly choosing an edge and rewiring one end to a preferentially chosen node.

    3) With $(1 - p - q)$ probability, $m$ new nodes are added to the graph
    with edges attached preferentially.

    When $p = q = 0$, the model behaves just like the BarabÃ¡siâ€“Alber model.

    Parameters
    ----------
    n : int
        Number of nodes
    m : int
        Number of edges with which a new node attaches to existing nodes
    p : float
        Probability value for adding an edge between existing nodes. p + q < 1
    q : float
        Probability value of rewiring of existing edges. p + q < 1
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `m` does not satisfy ``1 <= m < n`` or ``1 >= p + q``

    References
    ----------
    .. [1] Albert, R., & BarabÃ¡si, A. L. (2000)
       Topology of evolving networks: local events and universality
       Physical review letters, 85(24), 5234.
    r   z7Extended Barabasi-Albert network needs m>=1 and m<n, m=z, n=z5Extended Barabasi-Albert network needs p + q <= 1, p=z, q=r   c                    s   g | ]\}}|ˆ k r|‘qS r.   r.   ©rX   ÚndÚdeg©Úclique_degreer.   r/   r[   b  s      z2extended_barabasi_albert_graph.<locals>.<listcomp>c                    s   g | ]}|ˆ kr|‘qS r.   r.   ©rX   rt   )Úprohibited_nodesr.   r/   r[   m  s      c                    s,   g | ]$\}}d |  k r ˆ k rn q|‘qS ©r   r.   rs   rv   r.   r/   r[   „  s
      
  c                    s   g | ]}|ˆ kr|‘qS r.   r.   rx   )Úneighbor_nodesr.   r/   r[   “  s      r   )r!   rD   r   rl   r3   r%   rF   ÚsizerG   r?   r>   Úappendr'   ÚremoverL   rg   rJ   rK   )r(   r:   r)   Úqr   Úmsgr*   Zattachment_preferenceÚnew_nodeZa_probabilityZclique_sizeZelligible_nodesrI   Zsrc_nodeZ	dest_noderY   rM   r.   )rw   r{   ry   r/   r     sx    1




ÿ


ÿþB


ÿ





c           
         s:  |dk s| |k r&t  d|› d| › ¡‚|dks6|dk rFt  d|› ¡‚t|ƒ‰ tˆ  ¡ ƒ}|‰ˆ| k r6t|||ƒ}| ¡ }ˆ  ˆ|¡ | |¡ d}||k r| 	¡ |k rô‡ ‡fdd„ˆ  
|¡D ƒ}|rô| |¡}	ˆ  ˆ|	¡ | |	¡ |d }q–| ¡ }ˆ  ˆ|¡ | |¡ |d }q–| ˆg| ¡ ˆd7 ‰q^ˆ S )u)  Holme and Kim algorithm for growing graphs with powerlaw
    degree distribution and approximate average clustering.

    Parameters
    ----------
    n : int
        the number of nodes
    m : int
        the number of random edges to add for each new node
    p : float,
        Probability of adding a triangle after adding a random edge
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Notes
    -----
    The average clustering has a hard time getting above a certain
    cutoff that depends on `m`.  This cutoff is often quite low.  The
    transitivity (fraction of triangles to possible triangles) seems to
    decrease with network size.

    It is essentially the BarabÃ¡siâ€“Albert (BA) growth model with an
    extra step that each random edge is followed by a chance of
    making an edge to one of its neighbors too (and thus a triangle).

    This algorithm improves on BA in the sense that it enables a
    higher average clustering to be attained if desired.

    It seems possible to have a disconnected graph with this algorithm
    since the initial `m` nodes may not be all linked to a new node
    on the first iteration like the BA model.

    Raises
    ------
    NetworkXError
        If `m` does not satisfy ``1 <= m <= n`` or `p` does not
        satisfy ``0 <= p <= 1``.

    References
    ----------
    .. [1] P. Holme and B. J. Kim,
       "Growing scale-free networks with tunable clustering",
       Phys. Rev. E, 65, 026107, 2002.
    r   z'NetworkXError must have m>1 and m<n, m=z,n=r   z$NetworkXError p must be in [0,1], p=c                    s$   g | ]}ˆ   ˆ|¡s|ˆkr|‘qS r.   )r@   )rX   Únbr©r*   ro   r.   r/   r[   ù  s    þz*powerlaw_cluster_graph.<locals>.<listcomp>)r!   rD   r   r>   rE   rg   Úpopr'   r}   r%   Z	neighborsr?   rl   )
r(   r:   r)   r   rn   Zpossible_targetsÚtargetÚcountZneighborhoodr‚   r.   rƒ   r/   r   ¶  s>    0


þ




c                 C   s´   t |ƒt |ƒ }}tdd„ ||fD ƒƒr2t d¡‚td| ¡  |  d ƒ}t|ƒ}|d }t|ƒD ]L} | ¡ |k rb|d7 }| | |¡ |}| ¡ |k rf|d7 }| ||¡ qŠqfqb|S )a0  Returns a random lobster graph.

    A lobster is a tree that reduces to a caterpillar when pruning all
    leaf nodes. A caterpillar is a tree that reduces to a path graph
    when pruning all leaf nodes; setting `p2` to zero produces a caterpillar.

    This implementation iterates on the probabilities `p1` and `p2` to add
    edges at levels 1 and 2, respectively. Graphs are therefore constructed
    iteratively with uniform randomness at each level rather than being selected
    uniformly at random from the set of all possible lobsters.

    Parameters
    ----------
    n : int
        The expected number of nodes in the backbone
    p1 : float
        Probability of adding an edge to the backbone
    p2 : float
        Probability of adding an edge one level beyond backbone
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Raises
    ------
    NetworkXError
        If `p1` or `p2` parameters are >= 1 because the while loops would never finish.
    c                 s   s   | ]}|d kV  qdS )r   Nr.   )rX   r)   r.   r.   r/   Ú	<genexpr>.  s     z!random_lobster.<locals>.<genexpr>z6Probability values for `p1` and `p2` must both be < 1.r   g      à?r   )	ÚabsÚanyr!   rD   r&   r%   r   r3   r'   )r(   Úp1Úp2r   ZllenÚLZcurrent_nodeZcat_noder.   r.   r/   r     s    
c                 C   s  t dƒ}g }g }d}| D ]\\}}}t|| ƒ}	| ||	 ¡ tjt||	|d|d}
| |
¡ ||7 }tj ||
¡}qtt	|ƒd ƒD ]v}t
|| ƒ}t
||d  ƒ}|| }d}||k r†| |¡}| |¡}||ks²| ||¡ræq²q²| ||¡ |d }q²q†|S )aa  Returns a random shell graph for the constructor given.

    Parameters
    ----------
    constructor : list of three-tuples
        Represents the parameters for a shell, starting at the center
        shell.  Each element of the list must be of the form `(n, m,
        d)`, where `n` is the number of nodes in the shell, `m` is
        the number of edges in the shell, and `d` is the ratio of
        inter-shell (next) edges to intra-shell edges. If `d` is zero,
        there will be no intra-shell edges, and if `d` is one there
        will be all possible intra-shell edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Examples
    --------
    >>> constructor = [(10, 20, 0.8), (20, 40, 0.8)]
    >>> G = nx.random_shell_graph(constructor)

    r   )r   )Zfirst_labelr   )r   r&   r}   r!   Zconvert_node_labels_to_integersr   Ú	operatorsÚunionr3   rF   r>   r?   r@   r'   )Úconstructorr   r*   ZglistZintra_edgesZnnodesr(   r:   rb   Zinter_edgesÚgÚgiZnlist1Znlist2Ztotal_edgesrB   r;   r+   r.   r.   r/   r   A  s6     ÿ


c                 C   s   t | |||d}t|ƒ}|S )a:  Returns a tree with a power law degree distribution.

    Parameters
    ----------
    n : int
        The number of nodes.
    gamma : float
        Exponent of the power law.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    tries : int
        Number of attempts to adjust the sequence to make it a tree.

    Raises
    ------
    NetworkXError
        If no valid sequence is found within the maximum number of
        attempts.

    Notes
    -----
    A trial power law degree sequence is chosen and then elements are
    swapped with new elements from a powerlaw distribution until the
    sequence makes a tree (by checking, for example, that the number of
    edges is one smaller than the number of nodes).

    )Úgammar   rP   )r   r	   )r(   r’   r   rP   rd   r*   r.   r.   r/   r   z  s    c           	         s    t jjˆ ||d}‡ fdd„|D ƒ}t jj|||d}‡ fdd„|D ƒ}|D ]<}dˆ  t|ƒ dkrl|  S | dˆ d ¡}| ¡ ||< qLt  d|› d	¡‚d
S )aK  Returns a degree sequence for a tree with a power law distribution.

    Parameters
    ----------
    n : int,
        The number of nodes.
    gamma : float
        Exponent of the power law.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    tries : int
        Number of attempts to adjust the sequence to make it a tree.

    Raises
    ------
    NetworkXError
        If no valid sequence is found within the maximum number of
        attempts.

    Notes
    -----
    A trial power law degree sequence is chosen and then elements are
    swapped with new elements from a power law distribution until
    the sequence makes a tree (by checking, for example, that the number of
    edges is one smaller than the number of nodes).

    )Úexponentr   c                    s    g | ]}t ˆ tt|ƒd ƒƒ‘qS rz   ©Úminrp   Úround©rX   Ús©r(   r.   r/   r[   ¿  s     z1random_powerlaw_tree_sequence.<locals>.<listcomp>c                    s    g | ]}t ˆ tt|ƒd ƒƒ‘qS rz   r”   r—   r™   r.   r/   r[   Ä  s     r   r   r   zExceeded max (z%) attempts for a valid tree sequence.N)r!   ÚutilsZpowerlaw_sequenceÚsumÚrandintr„   rD   )	r(   r’   r   rP   ÚzZzseqZswapru   Úindexr.   r™   r/   r   ž  s    
ÿc           	         sÄ   |dkr&ddl ‰ddl}‡ ‡fdd„}t ¡ }| t| ƒ¡ d\}}|| k rÀt d| ¡  ¡ }ˆ ||  ||  dƒ|krŒ|d |d  }}qDt 	| |||  ||  |ƒ ¡}| 
|d |d ¡ qD|S )uñ  Returns an random graph based on the specified kernel.

    The algorithm chooses each of the $[n(n-1)]/2$ possible edges with
    probability specified by a kernel $\kappa(x,y)$ [1]_.  The kernel
    $\kappa(x,y)$ must be a symmetric (in $x,y$), non-negative,
    bounded function.

    Parameters
    ----------
    n : int
        The number of nodes
    kernel_integral : function
        Function that returns the definite integral of the kernel $\kappa(x,y)$,
        $F(y,a,b) := \int_a^b \kappa(x,y)dx$
    kernel_root: function (optional)
        Function that returns the root $b$ of the equation $F(y,a,b) = r$.
        If None, the root is found using :func:`scipy.optimize.brentq`
        (this requires SciPy).
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Notes
    -----
    The kernel is specified through its definite integral which must be
    provided as one of the arguments. If the integral and root of the
    kernel integral can be found in $O(1)$ time then this algorithm runs in
    time $O(n+m)$ where m is the expected number of edges [2]_.

    The nodes are set to integers from $0$ to $n-1$.

    Examples
    --------
    Generate an ErdÅ‘sâ€“RÃ©nyi random graph $G(n,c/n)$, with kernel
    $\kappa(x,y)=c$ where $c$ is the mean expected degree.

    >>> def integral(u, w, z):
    ...     return c * (z - w)
    >>> def root(u, w, r):
    ...     return r / c + w
    >>> c = 1
    >>> graph = nx.random_kernel_graph(1000, integral, root)

    See Also
    --------
    gnp_random_graph
    expected_degree_graph

    References
    ----------
    .. [1] BollobÃ¡s, BÃ©la,  Janson, S. and Riordan, O.
       "The phase transition in inhomogeneous random graphs",
       *Random Structures Algorithms*, 31, 3--122, 2007.

    .. [2] Hagberg A, Lemons N (2015),
       "Fast Generation of Sparse Random Kernel Graphs".
       PLoS ONE 10(9): e0135177, 2015. doi:10.1371/journal.pone.0135177
    Nr   c                    s"   ‡ ‡‡‡fdd„}ˆj  |ˆ d¡S )Nc                    s   ˆˆˆ | ƒˆ S )Nr.   )Úb)ÚaÚkernel_integralÚrÚyr.   r/   Úmy_function  s    z=random_kernel_graph.<locals>.kernel_root.<locals>.my_functionr   )ÚoptimizeZbrentq)r£   r    r¢   r¤   ©r¡   Úsp)r    r¢   r£   r/   Úkernel_root  s    z(random_kernel_graph.<locals>.kernel_root)r   r   r   )ÚscipyZscipy.optimizer!   r5   r6   r3   r"   r#   r%   Úceilr'   )	r(   r¡   r¨   r   r©   ÚgraphrI   rH   r¢   r.   r¦   r/   r   Ö  s    <)NF)NF)N)NF)N)N)rO   N)N)NN)NN)N)N)N)N)rC   NrO   )rC   NrO   )NN)%Ú__doc__r1   r"   Úcollectionsr   Znetworkxr!   Znetworkx.utilsr   Zclassicr   r   r   r   Z
degree_seqr	   Ú__all__r
   r   r   r   r   r   r   r   r   r   rg   r   r   r   r   r   r   r   r   r   r.   r.   r.   r/   Ú<module>   s‚   íF;<6EI3rGb #X18#7