Files
agent_compositor_test/references/igraph-1.0.1/doc/html/igraph-Layout.html
T
Abdelrahman Said a11edf0c53 Add graph references
2026-06-28 13:49:01 +01:00

3778 lines
134 KiB
HTML
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Chapter 29. Generating layouts for graph drawing</title>
<meta name="generator" content="DocBook XSL Stylesheets Vsnapshot">
<link rel="home" href="index.html" title="igraph Reference Manual">
<link rel="up" href="index.html" title="igraph Reference Manual">
<link rel="prev" href="igraph-Embedding.html" title="Chapter 28. Embedding of graphs">
<link rel="next" href="igraph-Processes.html" title="Chapter 30. Processes on graphs">
<script type="text/javascript" src="toggle.js"></script><link rel="stylesheet" href="style.css" type="text/css">
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/font-awesome/4.7.0/css/font-awesome.min.css" type="text/css">
<link rel="chapter" href="igraph-Introduction.html" title="Chapter 1. Introduction">
<link rel="chapter" href="igraph-Installation.html" title="Chapter 2. Installation">
<link rel="chapter" href="igraph-Tutorial.html" title="Chapter 3. Tutorial">
<link rel="chapter" href="igraph-Basic.html" title="Chapter 4. Basic data types and interface">
<link rel="chapter" href="igraph-Error.html" title="Chapter 5. Error handling">
<link rel="chapter" href="igraph-Memory.html" title="Chapter 6. Memory (de)allocation">
<link rel="chapter" href="igraph-Data-structures.html" title="Chapter 7. Data structure library: vector, matrix, other data types">
<link rel="chapter" href="igraph-Random.html" title="Chapter 8. Random numbers">
<link rel="chapter" href="igraph-Iterators.html" title="Chapter 9. Vertex and edge selectors and sequences, iterators">
<link rel="chapter" href="igraph-Attributes.html" title="Chapter 10. Graph, vertex and edge attributes">
<link rel="chapter" href="igraph-Generators.html" title="Chapter 11. Deterministic graph generators">
<link rel="chapter" href="igraph-Games.html" title='Chapter 12. Stochastic graph generators ("games")'>
<link rel="chapter" href="igraph-Bipartite.html" title="Chapter 13. Bipartite, i.e. two-mode graphs">
<link rel="chapter" href="igraph-Spatial.html" title="Chapter 14. Spatial graphs">
<link rel="chapter" href="igraph-Operators.html" title="Chapter 15. Graph operators">
<link rel="chapter" href="igraph-Visitors.html" title="Chapter 16. Graph visitors">
<link rel="chapter" href="igraph-Structural.html" title="Chapter 17. Structural properties of graphs">
<link rel="chapter" href="igraph-Cycles.html" title="Chapter 18. Graph cycles">
<link rel="chapter" href="igraph-Cliques.html" title="Chapter 19. Cliques and independent vertex sets">
<link rel="chapter" href="igraph-Motifs.html" title="Chapter 20. Graph motifs, dyad census and triad census">
<link rel="chapter" href="igraph-Isomorphism.html" title="Chapter 21. Graph isomorphism">
<link rel="chapter" href="igraph-Coloring.html" title="Chapter 22. Graph coloring">
<link rel="chapter" href="igraph-Flows.html" title="Chapter 23. Maximum flows, minimum cuts and related measures">
<link rel="chapter" href="igraph-Separators.html" title="Chapter 24. Vertex separators">
<link rel="chapter" href="igraph-Community.html" title="Chapter 25. Detecting community structure">
<link rel="chapter" href="igraph-Graphlets.html" title="Chapter 26. Graphlets">
<link rel="chapter" href="igraph-HRG.html" title="Chapter 27. Hierarchical random graphs">
<link rel="chapter" href="igraph-Embedding.html" title="Chapter 28. Embedding of graphs">
<link rel="chapter" href="igraph-Layout.html" title="Chapter 29. Generating layouts for graph drawing">
<link rel="chapter" href="igraph-Processes.html" title="Chapter 30. Processes on graphs">
<link rel="chapter" href="igraph-Foreign.html" title="Chapter 31. Reading and writing graphs from and to files">
<link rel="chapter" href="igraph-Linalg.html" title="Chapter 32. Using BLAS, LAPACK and ARPACK for igraph matrices and graphs">
<link rel="chapter" href="igraph-Nongraph.html" title="Chapter 33. Non-graph related functions">
<link rel="chapter" href="igraph-Advanced.html" title="Chapter 34. Advanced igraph programming">
<link rel="chapter" href="igraph-Glossary.html" title="Chapter 35. Glossary">
<link rel="chapter" href="igraph-Licenses.html" title="Chapter 36. Licenses for igraph and this manual">
<link rel="index" href="ix01.html" title="Index">
</head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<div class="navigation-header mb-4" width="100%" summary="Navigation header"><div class="btn-group">
<a accesskey="p" class="btn btn-light" href="igraph-Embedding.html"><i class="fa fa-chevron-left"></i>
Previous
</a><a accesskey="h" class="btn btn-light" href="index.html"><i class="fa fa-home"></i>
Home
</a><a accesskey="n" class="btn btn-light" href="igraph-Processes.html"><i class="fa fa-chevron-right"></i>
Next
</a>
</div></div>
<div class="chapter">
<div class="titlepage"><div><div><h1 class="title">
<a name="igraph-Layout"></a>Chapter 29. Generating layouts for graph drawing</h1></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="igraph-Layout.html#two-d-layout-generators">1. 2D layout generators</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#layouts-for-trees-and-acyclic-graphs">2. Layouts for trees and acyclic graphs</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#three-d-layout-generators">3. 3D layout generators</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#pp-layouts">4. Post-processing layouts</a></span></dt>
</dl></div>
<div class="section">
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="two-d-layout-generators"></a>1. 2D layout generators</h2></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_random">1.1. <code class="function">igraph_layout_random</code> — Places the vertices uniformly randomly within a square.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_circle">1.2. <code class="function">igraph_layout_circle</code> — Places the vertices uniformly on a circle in arbitrary order.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_star">1.3. <code class="function">igraph_layout_star</code> — Generates a star-like layout.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_grid">1.4. <code class="function">igraph_layout_grid</code> — Places the vertices on a regular grid on the plane.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_graphopt">1.5. <code class="function">igraph_layout_graphopt</code> — Optimizes vertex layout via the graphopt algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_bipartite">1.6. <code class="function">igraph_layout_bipartite</code> — Simple layout for bipartite graphs.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#drl-layout-generator">1.7. The DrL layout generator</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_fruchterman_reingold">1.8. <code class="function">igraph_layout_fruchterman_reingold</code> — Places the vertices on a plane according to the Fruchterman-Reingold algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_kamada_kawai">1.9. <code class="function">igraph_layout_kamada_kawai</code> — Places the vertices on a plane according to the Kamada-Kawai algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_gem">1.10. <code class="function">igraph_layout_gem</code> — Layout graph according to GEM algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_davidson_harel">1.11. <code class="function">igraph_layout_davidson_harel</code> — Davidson-Harel layout algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_mds">1.12. <code class="function">igraph_layout_mds</code> — Place the vertices on a plane using multidimensional scaling.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_lgl">1.13. <code class="function">igraph_layout_lgl</code> — Force based layout algorithm for large graphs.</a></span></dt>
</dl></div>
<p>Layout generator functions (or at least most of them) try to place the
vertices and edges of a graph on a 2D plane or in 3D space in a way
which visually pleases the human eye.</p>
<p>They take a graph object and a number of parameters as arguments
and return an <span class="type">igraph_matrix_t</span>, in which each row gives the
coordinates of a vertex.</p>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_random"></a>1.1. <code class="function">igraph_layout_random</code> — Places the vertices uniformly randomly within a square.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.4.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_random(const igraph_t *graph, igraph_matrix_t *res);
</pre></div>
<p>
</p>
<p>
Vertex coordinates range from -1 to 1, and are placed in two columns
of a matrix, with a row for each vertex.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|), the number of vertices.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_circle"></a>1.2. <code class="function">igraph_layout_circle</code> — Places the vertices uniformly on a circle in arbitrary order.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.5.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_circle(const igraph_t *graph, igraph_matrix_t *res,
igraph_vs_t order);
</pre></div>
<p>
</p>
<p>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>order</code></em>:</span></p></td>
<td><p>
The order of the vertices on the circle. The vertices
not included here, will be placed at (0,0). Supply
<a class="link" href="igraph-Iterators.html#igraph_vss_all" title="4.1. igraph_vss_all — All vertices of a graph (immediate version)."><code class="function">igraph_vss_all()</code></a> here to place vertices in the
order of their vertex IDs.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|), the number of vertices.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_star"></a>1.3. <code class="function">igraph_layout_star</code> — Generates a star-like layout.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.6.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_star(const igraph_t *graph, igraph_matrix_t *res,
igraph_int_t center, const igraph_vector_int_t *order);
</pre></div>
<p>
</p>
<p>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph. Its edges are ignored by this function.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>center</code></em>:</span></p></td>
<td><p>
The id of the vertex to put in the center. You can set it to
any arbitrary value for the special case when the input graph has no
vertices; otherwise it must be between 0 and the number of vertices
minus 1.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>order</code></em>:</span></p></td>
<td><p>
A numeric vector giving the order of the vertices
(including the center vertex!). If a null pointer, then the
vertices are placed in increasing vertex ID order.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|), linear in the number of vertices.
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_circle" title="1.2. igraph_layout_circle — Places the vertices uniformly on a circle in arbitrary order."><code class="function">igraph_layout_circle()</code></a> and other layout generators.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_grid"></a>1.4. <code class="function">igraph_layout_grid</code> — Places the vertices on a regular grid on the plane.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.7.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_grid(const igraph_t *graph, igraph_matrix_t *res, igraph_int_t width);
</pre></div>
<p>
</p>
<p>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>width</code></em>:</span></p></td>
<td><p>
The number of vertices in a single row of the grid.
When zero or negative, the width of the grid will be the
square root of the number of vertices, rounded up if needed.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code. The current implementation always returns with
success.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|), the number of vertices.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_graphopt"></a>1.5. <code class="function">igraph_layout_graphopt</code> — Optimizes vertex layout via the graphopt algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.8.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_graphopt(const igraph_t *graph, igraph_matrix_t *res,
igraph_int_t niter,
igraph_real_t node_charge, igraph_real_t node_mass,
igraph_real_t spring_length,
igraph_real_t spring_constant,
igraph_real_t max_sa_movement,
igraph_bool_t use_seed);
</pre></div>
<p>
</p>
<p>
This is a port of the graphopt layout algorithm by Michael Schmuhl.
graphopt version 0.4.1 was rewritten in C, the support for
layers was removed and the code was reorganized to avoid some
unnecessary steps when the node charge (see below) is zero.
</p>
<p>
Graphopt uses physical analogies for defining attracting and repelling
forces among the vertices and then the physical system is simulated
until it reaches an equilibrium. (There is no simulated annealing or
anything like that, so a stable fixed point is not guaranteed.)
</p>
<p>
See also
<a class="ulink" href="https://web.archive.org/web/20220611030748/http://www.schmuhl.org/graphopt/" target="_top">https://web.archive.org/web/20220611030748/http://www.schmuhl.org/graphopt/</a>
and
<a class="ulink" href="https://sourceforge.net/projects/graphopt/" target="_top">https://sourceforge.net/projects/graphopt/</a>
for the original graphopt.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix, the result will be stored here
and its initial contents are used as the starting point of the simulation
if the <em class="parameter"><code>use_seed</code></em> argument is true. Note that in this case the
matrix should have the proper size, otherwise a warning is issued and
the supplied values are ignored. If no starting positions are given
(or they are invalid) then a random starting position is used.
The matrix will be resized if needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>niter</code></em>:</span></p></td>
<td><p>
Integer constant, the number of iterations to perform.
Should be a couple of hundred in general. If you have a large graph
then you might want to only do a few iterations and then check the
result. If it is not good enough you can feed it in again in
the <em class="parameter"><code>res</code></em> argument. The original graphopt default is 500.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>node_charge</code></em>:</span></p></td>
<td><p>
The charge of the vertices, used to calculate electric
repulsion. The original graphopt default is 0.001.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>node_mass</code></em>:</span></p></td>
<td><p>
The mass of the vertices, used for the spring forces.
The original graphopt defaults to 30.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>spring_length</code></em>:</span></p></td>
<td><p>
The length of the springs.
The original graphopt defaults to zero.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>spring_constant</code></em>:</span></p></td>
<td><p>
The spring constant, the original graphopt defaults
to one.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>max_sa_movement</code></em>:</span></p></td>
<td><p>
Real constant, it gives the maximum amount of movement
allowed in a single step along a single axis. The original graphopt
default is 5.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, whether to use the positions in <em class="parameter"><code>res</code></em> as
a starting configuration. See also <em class="parameter"><code>res</code></em> above.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(n (|V|^2+|E|) ), n is the number of iterations,
|V| is the number of vertices, |E| the number
of edges. If <em class="parameter"><code>node_charge</code></em> is zero then it is only O(n|E|).
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_bipartite"></a>1.6. <code class="function">igraph_layout_bipartite</code> — Simple layout for bipartite graphs.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.9.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_bipartite(const igraph_t *graph,
const igraph_vector_bool_t *types,
igraph_matrix_t *res, igraph_real_t hgap,
igraph_real_t vgap, igraph_int_t maxiter);
</pre></div>
<p>
</p>
<p>
The layout is created by first placing the vertices in two rows,
according to their types. Then the positions within the rows are
optimized to minimize edge crossings, by calling <a class="link" href="igraph-Layout.html#igraph_layout_sugiyama" title="2.4. igraph_layout_sugiyama — Sugiyama layout algorithm for layered directed acyclic graphs."><code class="function">igraph_layout_sugiyama()</code></a>.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>types</code></em>:</span></p></td>
<td><p>
A boolean vector containing ones and zeros, the vertex
types. Its length must match the number of vertices in the graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix, the result, the x and
y coordinates are stored here.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>hgap</code></em>:</span></p></td>
<td><p>
The preferred minimum horizontal gap between vertices
in the same layer (i.e. vertices of the same type).
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>vgap</code></em>:</span></p></td>
<td><p>
The distance between layers.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxiter</code></em>:</span></p></td>
<td><p>
Maximum number of iterations in the crossing
minimization stage. 100 is a reasonable default; if you feel
that you have too many edge crossings, increase this.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_sugiyama" title="2.4. igraph_layout_sugiyama — Sugiyama layout algorithm for layered directed acyclic graphs."><code class="function">igraph_layout_sugiyama()</code></a>.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="drl-layout-generator"></a>1.7. The DrL layout generator</h3></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_drl_options_t">1.7.1. <code class="function">igraph_layout_drl_options_t</code> — Parameters for the DrL layout generator</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_drl_default_t">1.7.2. <code class="function">igraph_layout_drl_default_t</code> — Predefined parameter templates for the DrL layout generator</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_drl_options_init">1.7.3. <code class="function">igraph_layout_drl_options_init</code> — Initialize parameters for the DrL layout generator</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_drl">1.7.4. <code class="function">igraph_layout_drl</code> — The DrL layout generator</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_drl_3d">1.7.5. <code class="function">igraph_layout_drl_3d</code> — The DrL layout generator, 3d version.</a></span></dt>
</dl></div>
<p>
DrL is a sophisticated layout generator developed and implemented by
Shawn Martin et al. As of October 2012 the original DrL homepage is
unfortunately not available. You can read more about this algorithm
in the following technical report: Martin, S., Brown, W.M.,
Klavans, R., Boyack, K.W., DrL: Distributed Recursive (Graph)
Layout. SAND Reports, 2008. 2936: p. 1-10.
</p>
<p>
Only a subset of the complete DrL functionality is
included in igraph, parallel runs and recursive, multi-level
layouting is not supported.
</p>
<p>
The parameters of the layout are stored in an <a class="link" href="igraph-Layout.html#igraph_layout_drl_options_t" title="1.7.1. igraph_layout_drl_options_t — Parameters for the DrL layout generator"><code class="function">igraph_layout_drl_options_t</code></a> structure, this can be initialized by
calling the function <a class="link" href="igraph-Layout.html#igraph_layout_drl_options_init" title="1.7.3. igraph_layout_drl_options_init — Initialize parameters for the DrL layout generator"><code class="function">igraph_layout_drl_options_init()</code></a>.
The fields of this structure can then be adjusted by hand if needed.
The layout is calculated by an <a class="link" href="igraph-Layout.html#igraph_layout_drl" title="1.7.4. igraph_layout_drl — The DrL layout generator"><code class="function">igraph_layout_drl()</code></a> call.
</p>
<div class="section">
<div class="titlepage"><div><div><h4 class="title">
<a name="igraph_layout_drl_options_t"></a>1.7.1. <code class="function">igraph_layout_drl_options_t</code> — Parameters for the DrL layout generator</h4></div></div></div>
<a class="indexterm" name="id-1.30.2.10.5.2"></a><p>
</p>
<pre class="programlisting">
typedef struct igraph_layout_drl_options_t {
igraph_real_t edge_cut;
igraph_int_t init_iterations;
igraph_real_t init_temperature;
igraph_real_t init_attraction;
igraph_real_t init_damping_mult;
igraph_int_t liquid_iterations;
igraph_real_t liquid_temperature;
igraph_real_t liquid_attraction;
igraph_real_t liquid_damping_mult;
igraph_int_t expansion_iterations;
igraph_real_t expansion_temperature;
igraph_real_t expansion_attraction;
igraph_real_t expansion_damping_mult;
igraph_int_t cooldown_iterations;
igraph_real_t cooldown_temperature;
igraph_real_t cooldown_attraction;
igraph_real_t cooldown_damping_mult;
igraph_int_t crunch_iterations;
igraph_real_t crunch_temperature;
igraph_real_t crunch_attraction;
igraph_real_t crunch_damping_mult;
igraph_int_t simmer_iterations;
igraph_real_t simmer_temperature;
igraph_real_t simmer_attraction;
igraph_real_t simmer_damping_mult;
} igraph_layout_drl_options_t;
</pre>
<p>
</p>
<p>
</p>
<p></p>
<p><b>Values: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><code class="constant">edge_cut</code>:</span></p></td>
<td><p>
The edge cutting parameter.
Edge cutting is done in the late stages of the
algorithm in order to achieve less dense layouts. Edges are cut
if there is a lot of stress on them (a large value in the
objective function sum). The edge cutting parameter is a value
between 0 and 1 with 0 representing no edge cutting and 1
representing maximal edge cutting. The default value is 32/40.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">init_iterations</code>:</span></p></td>
<td><p>
Number of iterations, initial phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">init_temperature</code>:</span></p></td>
<td><p>
Start temperature, initial phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">init_attraction</code>:</span></p></td>
<td><p>
Attraction, initial phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">init_damping_mult</code>:</span></p></td>
<td><p>
Damping factor, initial phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">liquid_iterations</code>:</span></p></td>
<td><p>
Number of iterations in the liquid phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">liquid_temperature</code>:</span></p></td>
<td><p>
Start temperature in the liquid phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">liquid_attraction</code>:</span></p></td>
<td><p>
Attraction in the liquid phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">liquid_damping_mult</code>:</span></p></td>
<td><p>
Multiplicatie damping factor, liquid phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">expansion_iterations</code>:</span></p></td>
<td><p>
Number of iterations in the expansion phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">expansion_temperature</code>:</span></p></td>
<td><p>
Start temperature in the expansion phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">expansion_attraction</code>:</span></p></td>
<td><p>
Attraction, expansion phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">expansion_damping_mult</code>:</span></p></td>
<td><p>
Damping factor, expansion phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">cooldown_iterations</code>:</span></p></td>
<td><p>
Number of iterations in the cooldown phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">cooldown_temperature</code>:</span></p></td>
<td><p>
Start temperature in the cooldown phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">cooldown_attraction</code>:</span></p></td>
<td><p>
Attraction in the cooldown phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">cooldown_damping_mult</code>:</span></p></td>
<td><p>
Damping fact int the cooldown phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">crunch_iterations</code>:</span></p></td>
<td><p>
Number of iterations in the crunch phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">crunch_temperature</code>:</span></p></td>
<td><p>
Start temperature in the crunch phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">crunch_attraction</code>:</span></p></td>
<td><p>
Attraction in the crunch phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">crunch_damping_mult</code>:</span></p></td>
<td><p>
Damping factor in the crunch phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">simmer_iterations</code>:</span></p></td>
<td><p>
Number of iterations in the simmer phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">simmer_temperature</code>:</span></p></td>
<td><p>
Start temperature in te simmer phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">simmer_attraction</code>:</span></p></td>
<td><p>
Attraction in the simmer phase.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">simmer_damping_mult</code>:</span></p></td>
<td><p>
Multiplicative damping factor in the simmer phase.</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h4 class="title">
<a name="igraph_layout_drl_default_t"></a>1.7.2. <code class="function">igraph_layout_drl_default_t</code> — Predefined parameter templates for the DrL layout generator</h4></div></div></div>
<a class="indexterm" name="id-1.30.2.10.6.2"></a><p>
</p>
<pre class="programlisting">
typedef enum { IGRAPH_LAYOUT_DRL_DEFAULT = 0,
IGRAPH_LAYOUT_DRL_COARSEN,
IGRAPH_LAYOUT_DRL_COARSEST,
IGRAPH_LAYOUT_DRL_REFINE,
IGRAPH_LAYOUT_DRL_FINAL
} igraph_layout_drl_default_t;
</pre>
<p>
</p>
<p>
These constants can be used to initialize a set of DrL parameters.
These can then be modified according to the user's needs.
</p>
<p><b>Values: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_LAYOUT_DRL_DEFAULT</code>:</span></p></td>
<td><p>
The deafult parameters.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_LAYOUT_DRL_COARSEN</code>:</span></p></td>
<td><p>
Slightly modified parameters to
get a coarser layout.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_LAYOUT_DRL_COARSEST</code>:</span></p></td>
<td><p>
An even coarser layout.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_LAYOUT_DRL_REFINE</code>:</span></p></td>
<td><p>
Refine an already calculated layout.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_LAYOUT_DRL_FINAL</code>:</span></p></td>
<td><p>
Finalize an already refined layout.</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h4 class="title">
<a name="igraph_layout_drl_options_init"></a>1.7.3. <code class="function">igraph_layout_drl_options_init</code> — Initialize parameters for the DrL layout generator</h4></div></div></div>
<a class="indexterm" name="id-1.30.2.10.7.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_drl_options_init(igraph_layout_drl_options_t *options,
igraph_layout_drl_default_t templ);
</pre></div>
<p>
</p>
<p>
This function can be used to initialize the struct holding the
parameters for the DrL layout generator. There are a number of
predefined templates available, it is a good idea to start from one
of these by modifying some parameters.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>options</code></em>:</span></p></td>
<td><p>
The struct to initialize.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>templ</code></em>:</span></p></td>
<td><p>
The template to use. Currently the following templates
are supplied: <code class="constant">IGRAPH_LAYOUT_DRL_DEFAULT</code>, <code class="constant">IGRAPH_LAYOUT_DRL_COARSEN</code>, <code class="constant">IGRAPH_LAYOUT_DRL_COARSEST</code>,
<code class="constant">IGRAPH_LAYOUT_DRL_REFINE</code> and <code class="constant">IGRAPH_LAYOUT_DRL_FINAL</code>.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(1).
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h4 class="title">
<a name="igraph_layout_drl"></a>1.7.4. <code class="function">igraph_layout_drl</code> — The DrL layout generator</h4></div></div></div>
<a class="indexterm" name="id-1.30.2.10.8.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_drl(const igraph_t *graph, igraph_matrix_t *res,
igraph_bool_t use_seed,
const igraph_layout_drl_options_t *options,
const igraph_vector_t *weights);
</pre></div>
<p>
</p>
<p>
This function implements the force-directed DrL layout generator.
Please see more in the following technical report: Martin, S.,
Brown, W.M., Klavans, R., Boyack, K.W., DrL: Distributed Recursive
(Graph) Layout. SAND Reports, 2008. 2936: p. 1-10.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, if true, then the coordinates
supplied in the <em class="parameter"><code>res</code></em> argument are used as starting points.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to a matrix, the result layout is stored
here. It will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>options</code></em>:</span></p></td>
<td><p>
The parameters to pass to the layout generator.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
Edge weights, pointer to a vector. If this is a null
pointer then every edge will have the same weight.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: ???.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h4 class="title">
<a name="igraph_layout_drl_3d"></a>1.7.5. <code class="function">igraph_layout_drl_3d</code> — The DrL layout generator, 3d version.</h4></div></div></div>
<a class="indexterm" name="id-1.30.2.10.9.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_drl_3d(const igraph_t *graph, igraph_matrix_t *res,
igraph_bool_t use_seed,
const igraph_layout_drl_options_t *options,
const igraph_vector_t *weights);
</pre></div>
<p>
</p>
<p>
This function implements the force-directed DrL layout generator.
Please see more in the technical report: Martin, S., Brown, W.M.,
Klavans, R., Boyack, K.W., DrL: Distributed Recursive (Graph)
Layout. SAND Reports, 2008. 2936: p. 1-10.
</p>
<p> This function uses a modified DrL generator that does
the layout in three dimensions.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, if true, then the coordinates
supplied in the <em class="parameter"><code>res</code></em> argument are used as starting points.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to a matrix, the result layout is stored
here. It will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>options</code></em>:</span></p></td>
<td><p>
The parameters to pass to the layout generator.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
Edge weights, pointer to a vector. If this is a null
pointer then every edge will have the same weight.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: ???.
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_drl" title="1.7.4. igraph_layout_drl — The DrL layout generator"><code class="function">igraph_layout_drl()</code></a> for the standard 2d version.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_fruchterman_reingold"></a>1.8. <code class="function">igraph_layout_fruchterman_reingold</code> — Places the vertices on a plane according to the Fruchterman-Reingold algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.11.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_fruchterman_reingold(const igraph_t *graph,
igraph_matrix_t *res,
igraph_bool_t use_seed,
igraph_int_t niter,
igraph_real_t start_temp,
igraph_layout_grid_t grid,
const igraph_vector_t *weights,
const igraph_vector_t *minx,
const igraph_vector_t *maxx,
const igraph_vector_t *miny,
const igraph_vector_t *maxy);
</pre></div>
<p>
</p>
<p>
</p>
<p>
This is a force-directed layout that simulates an attractive force <code class="constant">f_a</code> between
connected vertex pairs and a repulsive force <code class="constant">f_r</code> between all vertex pairs.
The forces are computed as a function of the distance <code class="constant">d</code> between the two vertices as
</p>
<p>
<code class="literal">f_a(d) = -w * d^2</code> and <code class="literal">f_r(d) = 1/d</code>,
</p>
<p>
where <code class="constant">w</code> represents the edge weight. The equilibrium distance of two connected
vertices is thus <code class="literal">1/w^3</code>, assuming no other forces acting on them.
</p>
<p>
In disconnected graphs, igraph effectively inserts a weak connection of weight
<code class="literal">n^(-3/2)</code> between all pairs of vertices, where <code class="constant">n</code> is the vertex count.
This ensures that components are kept near each other.
</p>
<p>
Reference:
</p>
<p>
Fruchterman, T.M.J. and Reingold, E.M.:
Graph Drawing by Force-directed Placement.
Software -- Practice and Experience, 21/11, 1129--1164,
1991. <a class="ulink" href="https://doi.org/10.1002/spe.4380211102" target="_top">https://doi.org/10.1002/spe.4380211102</a>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
If true the supplied values in the
<em class="parameter"><code>res</code></em> argument are used as an initial layout, if
false a random initial layout is used.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>niter</code></em>:</span></p></td>
<td><p>
The number of iterations to do. A reasonable
default value is 500.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>start_temp</code></em>:</span></p></td>
<td><p>
Start temperature. This is the maximum amount
of movement allowed along one axis, within one step, for a
vertex. Currently it is decreased linearly to zero during
the iteration.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>grid</code></em>:</span></p></td>
<td><p>
Whether to use the (fast but less accurate) grid based
version of the algorithm. Possible values: <code class="constant">IGRAPH_LAYOUT_GRID</code>, <code class="constant">IGRAPH_LAYOUT_NOGRID</code>, <code class="constant">IGRAPH_LAYOUT_AUTOGRID</code>. The last one uses the grid based
version only for large graphs, currently the ones with
more than 1000 vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
Pointer to a vector containing edge weights. Weights must
be positive. If <code class="constant">NULL</code>, all edges are assumed to have weight 1.
The attraction along the edges will be multiplied by the weights,
resulting in vertices connected by a high-weight edge being placed
closer together.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>minx</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">x</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxx</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>minx</code></em>, but the maximum <span class="quote"><span class="quote">x</span></span>
coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>miny</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">y</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxy</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>miny</code></em>, but the maximum <span class="quote"><span class="quote">y</span></span>
coordinates.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|^2) in each
iteration, |V| is the number of
vertices in the graph.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_kamada_kawai"></a>1.9. <code class="function">igraph_layout_kamada_kawai</code> — Places the vertices on a plane according to the Kamada-Kawai algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.12.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_kamada_kawai(const igraph_t *graph, igraph_matrix_t *res,
igraph_bool_t use_seed, igraph_int_t maxiter,
igraph_real_t epsilon, igraph_real_t kkconst,
const igraph_vector_t *weights,
const igraph_vector_t *minx, const igraph_vector_t *maxx,
const igraph_vector_t *miny, const igraph_vector_t *maxy);
</pre></div>
<p>
</p>
<p>
This is a force-directed layout. A spring is inserted between all pairs
of vertices, both those which are directly connected and those that are not.
The unstretched length of springs is chosen based on the undirected graph distance
between the corresponding pair of vertices. Thus, in a weighted graph, increasing
the weight between two vertices pushes them apart. The Young modulus of springs
is inversely proportional to the graph distance, ensuring that springs between
far-apart veritces will have a smaller effect on the layout.
</p>
<p>
Disconnected graphs are handled by assuming that the graph distance between
vertices in different components is the same as the graph diameter.
</p>
<p>
This layout works particularly well for locally connected spatial networks
such as lattices.
</p>
<p>
This layout algorithm is not suitable for large graphs. The memory
requirements are of the order O(|V|^2).
</p>
<p>
Reference:
</p>
<p>
Kamada, T. and Kawai, S.:
An Algorithm for Drawing General Undirected Graphs.
Information Processing Letters, 31/1, 7--15, 1989.
<a class="ulink" href="https://doi.org/10.1016/0020-0190(89)90102-6" target="_top">https://doi.org/10.1016/0020-0190(89)90102-6</a>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
A graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result (x-positions in column zero and
y-positions in column one) and will be resized if needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, whether to use the values supplied in the
<em class="parameter"><code>res</code></em> argument as the initial configuration. If zero and there
are any limits on the X or Y coordinates, then a random initial
configuration is used. Otherwise the vertices are placed on a
circle of radius 1 as the initial configuration.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxiter</code></em>:</span></p></td>
<td><p>
The maximum number of iterations to perform. A reasonable
default value is at least ten (or more) times the number of
vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>epsilon</code></em>:</span></p></td>
<td><p>
Stop the iteration, if the maximum delta value of the
algorithm is smaller than this. It is safe to leave it at zero,
and then <em class="parameter"><code>maxiter</code></em> iterations are performed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>kkconst</code></em>:</span></p></td>
<td><p>
The Kamada-Kawai vertex attraction constant.
Typical value: number of vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
A vector of edge weights. Weights are interpreted as edge
<span class="emphasis"><em>lengths</em></span> in the shortest path calculation used by the
Kamada-Kawai algorithm. Therefore, vertices connected by high-weight
edges will be placed further apart. Pass <code class="constant">NULL</code> to assume unit weights
for all edges.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>minx</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">x</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxx</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>minx</code></em>, but the maximum <span class="quote"><span class="quote">x</span></span>
coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>miny</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">y</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxy</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>miny</code></em>, but the maximum <span class="quote"><span class="quote">y</span></span>
coordinates.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|) for each iteration, after an O(|V|^2
log|V|) initialization step. |V| is the number of vertices in the
graph.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_gem"></a>1.10. <code class="function">igraph_layout_gem</code> — Layout graph according to GEM algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.13.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_gem(const igraph_t *graph, igraph_matrix_t *res,
igraph_bool_t use_seed, igraph_int_t maxiter,
igraph_real_t temp_max, igraph_real_t temp_min,
igraph_real_t temp_init);
</pre></div>
<p>
</p>
<p>
The GEM layout algorithm, as described in Arne Frick, Andreas Ludwig,
Heiko Mehldau: A Fast Adaptive Layout Algorithm for Undirected Graphs,
Proc. Graph Drawing 1994, LNCS 894, pp. 388-403, 1995.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph. Edge directions are ignored in
directed graphs.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
The result is stored here. If the <em class="parameter"><code>use_seed</code></em> argument
is true, then this matrix is also used as the
starting point of the algorithm.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, whether to use the supplied coordinates in
<em class="parameter"><code>res</code></em> as the starting point. If false (zero), then a
uniform random starting point is used.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxiter</code></em>:</span></p></td>
<td><p>
The maximum number of iterations to
perform. Updating a single vertex counts as an iteration.
A reasonable default is 40 * n * n, where n is the number of
vertices. The original paper suggests 4 * n * n, but this
usually only works if the other parameters are set up carefully.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>temp_max</code></em>:</span></p></td>
<td><p>
The maximum allowed local temperature. A reasonable
default is the number of vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>temp_min</code></em>:</span></p></td>
<td><p>
The global temperature at which the algorithm
terminates (even before reaching <em class="parameter"><code>maxiter</code></em> iterations). A
reasonable default is 1/10.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>temp_init</code></em>:</span></p></td>
<td><p>
Initial local temperature of all vertices. A
reasonable default is the square root of the number of
vertices.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(t * n * (n+e)), where n is the number of vertices,
e is the number of edges and t is the number of time steps
performed.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_davidson_harel"></a>1.11. <code class="function">igraph_layout_davidson_harel</code> — Davidson-Harel layout algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.14.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_davidson_harel(const igraph_t *graph, igraph_matrix_t *res,
igraph_bool_t use_seed, igraph_int_t maxiter,
igraph_int_t fineiter, igraph_real_t cool_fact,
igraph_real_t weight_node_dist, igraph_real_t weight_border,
igraph_real_t weight_edge_lengths,
igraph_real_t weight_edge_crossings,
igraph_real_t weight_node_edge_dist);
</pre></div>
<p>
</p>
<p>
This function implements the algorithm by Davidson and Harel,
see Ron Davidson, David Harel: Drawing Graphs Nicely Using
Simulated Annealing. ACM Transactions on Graphics 15(4),
pp. 301-331, 1996.
<a class="ulink" href="https://doi.org/10.1145/234535.234538" target="_top">https://doi.org/10.1145/234535.234538</a>
</p>
<p>
The algorithm uses simulated annealing and a sophisticated
energy function, which is unfortunately hard to parameterize
for different graphs. The original publication did not disclose any
parameter values, and the ones below were determined by
experimentation.
</p>
<p>
The algorithm consists of two phases, an annealing phase, and a
fine-tuning phase. There is no simulated annealing in the second
phase.
</p>
<p>
Our implementation tries to follow the original publication, as
much as possible. The only major difference is that coordinates are
explicitly kept within the bounds of the rectangle of the layout.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The input graph, edge directions are ignored.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
A matrix, the result is stored here. It can be used to
supply start coordinates, see <em class="parameter"><code>use_seed</code></em>.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, whether to use the supplied <em class="parameter"><code>res</code></em> as
start coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxiter</code></em>:</span></p></td>
<td><p>
The maximum number of annealing iterations. A
reasonable value for smaller graphs is 10.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>fineiter</code></em>:</span></p></td>
<td><p>
The number of fine tuning iterations. A reasonable
value is <code class="literal">max(10, log2(n))</code> where <code class="constant">n</code> is the
number of vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>cool_fact</code></em>:</span></p></td>
<td><p>
Cooling factor. A reasonable value is 0.75.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weight_node_dist</code></em>:</span></p></td>
<td><p>
Weight for the node-node distances
component of the energy function. Reasonable value: 1.0.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weight_border</code></em>:</span></p></td>
<td><p>
Weight for the distance from the border
component of the energy function. It can be set to zero, if
vertices are allowed to sit on the border.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weight_edge_lengths</code></em>:</span></p></td>
<td><p>
Weight for the edge length component
of the energy function, a reasonable value is the density of
the graph divided by 10.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weight_edge_crossings</code></em>:</span></p></td>
<td><p>
Weight for the edge crossing component
of the energy function, a reasonable default is 1 minus the
square root of the density of the graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weight_node_edge_dist</code></em>:</span></p></td>
<td><p>
Weight for the node-edge distance
component of the energy function. A reasonable value is
1 minus the density, divided by 5.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: one first phase iteration has time complexity
O(n^2+m^2), one fine tuning iteration has time complexity O(mn).
Time complexity might be smaller if some of the weights of the
components of the energy function are set to zero.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_mds"></a>1.12. <code class="function">igraph_layout_mds</code> — Place the vertices on a plane using multidimensional scaling.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.15.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_mds(const igraph_t *graph, igraph_matrix_t *res,
const igraph_matrix_t *dist, igraph_int_t dim);
</pre></div>
<p>
</p>
<p>
This layout requires a distance matrix, where the intersection of
row i and column j specifies the desired distance between vertex i
and vertex j. The algorithm will try to place the vertices in a
space having a given number of dimensions in a way that approximates
the distance relations prescribed in the distance matrix. igraph
uses the classical multidimensional scaling by Torgerson; for more
details, see Cox &amp; Cox: Multidimensional Scaling (1994), Chapman
and Hall, London.
</p>
<p>
If the input graph is disconnected, igraph will decompose it
first into its subgraphs, lay out the subgraphs one by one
using the appropriate submatrices of the distance matrix, and
then merge the layouts using <a class="link" href="igraph-Layout.html#igraph_layout_merge_dla" title="4.1. igraph_layout_merge_dla — Merges multiple layouts by using a DLA algorithm."><code class="function">igraph_layout_merge_dla()</code></a>.
Since <a class="link" href="igraph-Layout.html#igraph_layout_merge_dla" title="4.1. igraph_layout_merge_dla — Merges multiple layouts by using a DLA algorithm."><code class="function">igraph_layout_merge_dla()</code></a> works for 2D layouts only,
you cannot run the MDS layout on disconnected graphs for
more than two dimensions.
</p>
<p>
Warning: if the graph is symmetric to the exchange of two vertices
(as is the case with leaves of a tree connecting to the same parent),
classical multidimensional scaling may assign the same coordinates to
these vertices.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
A graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized if needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>dist</code></em>:</span></p></td>
<td><p>
The distance matrix. It must be symmetric and this
function does not check whether the matrix is indeed
symmetric. Results are unspecified if you pass a non-symmetric
matrix here. You can set this parameter to null; in this
case, the undirected shortest path lengths between vertices
will be used as distances.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>dim</code></em>:</span></p></td>
<td><p>
The number of dimensions in the embedding space. For
2D layouts, supply 2 here.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.6.
</p>
<p>
Time complexity: usually around O(|V|^2 dim).
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_lgl"></a>1.13. <code class="function">igraph_layout_lgl</code> — Force based layout algorithm for large graphs.</h3></div></div></div>
<a class="indexterm" name="id-1.30.2.16.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_lgl(const igraph_t *graph, igraph_matrix_t *res,
igraph_int_t maxit, igraph_real_t maxdelta,
igraph_real_t area, igraph_real_t coolexp,
igraph_real_t repulserad, igraph_real_t cellsize,
igraph_int_t proot);
</pre></div>
<p>
</p>
<p>
</p>
<p>
This is a layout generator similar to the Large Graph Layout
algorithm and program (<a class="ulink" href="http://lgl.sourceforge.net/" target="_top">http://lgl.sourceforge.net/</a>). But unlike LGL, this
version uses a Fruchterman-Reingold style simulated annealing
algorithm for placing the vertices. The speedup is achieved by
placing the vertices on a grid and calculating the repulsion only
for vertices which are closer to each other than a limit.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The (initialized) graph object to place. It must be connnected;
disconnected graphs are not handled by the algorithm.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object to hold the
result. It will be resized if needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxit</code></em>:</span></p></td>
<td><p>
The maximum number of cooling iterations to perform
for each layout step. A reasonable default is 150.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxdelta</code></em>:</span></p></td>
<td><p>
The maximum length of the move allowed for a vertex
in a single iteration. A reasonable default is the number of
vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>area</code></em>:</span></p></td>
<td><p>
This parameter gives the area of the square on which
the vertices will be placed. A reasonable default value is the
number of vertices squared.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>coolexp</code></em>:</span></p></td>
<td><p>
The cooling exponent. A reasonable default value is
1.5.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>repulserad</code></em>:</span></p></td>
<td><p>
Determines the radius at which vertex-vertex
repulsion cancels out attraction of adjacent vertices. A
reasonable default value is <em class="parameter"><code>area</code></em> times the number of vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>cellsize</code></em>:</span></p></td>
<td><p>
The size of the grid cells, one side of the
square. A reasonable default value is the fourth root of
<em class="parameter"><code>area</code></em> (or the square root of the number of vertices if <em class="parameter"><code>area</code></em>
is also left at its default value).
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>proot</code></em>:</span></p></td>
<td><p>
The root vertex, this is placed first, its neighbors
in the first iteration, second neighbors in the second, etc. If
negative then a random vertex is chosen.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.2.</p>
<p>
Time complexity: ideally O(dia*maxit*(|V|+|E|)), |V| is the number
of vertices,
dia is the diameter of the graph, worst case complexity is still
O(dia*maxit*(|V|^2+|E|)), this is the case when all vertices happen to be
in the same grid cell.
</p>
</div>
</div>
<div class="section">
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="layouts-for-trees-and-acyclic-graphs"></a>2. Layouts for trees and acyclic graphs</h2></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_reingold_tilford">2.1. <code class="function">igraph_layout_reingold_tilford</code> — Reingold-Tilford layout for tree graphs.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_reingold_tilford_circular">2.2. <code class="function">igraph_layout_reingold_tilford_circular</code> — Circular Reingold-Tilford layout for trees.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_roots_for_tree_layout">2.3. <code class="function">igraph_roots_for_tree_layout</code> — Roots suitable for a nice tree layout.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_sugiyama">2.4. <code class="function">igraph_layout_sugiyama</code> — Sugiyama layout algorithm for layered directed acyclic graphs.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_umap">2.5. <code class="function">igraph_layout_umap</code> — Layout using Uniform Manifold Approximation and Projection (UMAP).</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_umap_compute_weights">2.6. <code class="function">igraph_layout_umap_compute_weights</code> — Compute weights for a UMAP layout starting from distances.</a></span></dt>
</dl></div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_reingold_tilford"></a>2.1. <code class="function">igraph_layout_reingold_tilford</code> — Reingold-Tilford layout for tree graphs.</h3></div></div></div>
<a class="indexterm" name="id-1.30.3.2.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_reingold_tilford(const igraph_t *graph,
igraph_matrix_t *res,
igraph_neimode_t mode,
const igraph_vector_int_t *roots,
const igraph_vector_int_t *rootlevel);
</pre></div>
<p>
</p>
<p>
</p>
<p>
Arranges the nodes in a tree where the given node is used as the root.
The tree is directed downwards and the parents are centered above its
children. For the exact algorithm, see:
</p>
<p>
Reingold, E and Tilford, J: Tidier drawing of trees.
IEEE Trans. Softw. Eng., SE-7(2):223--228, 1981.
<a class="ulink" href="https://doi.org/10.1109/TSE.1981.234519" target="_top">https://doi.org/10.1109/TSE.1981.234519</a>
</p>
<p>
If the given graph is not a tree, a breadth-first search is executed
first to obtain a possible spanning tree.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
The result, the coordinates in a matrix. The parameter
should point to an initialized matrix object and will be resized.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>mode</code></em>:</span></p></td>
<td><p>
Specifies which edges to consider when building the tree.
If it is <code class="constant">IGRAPH_OUT</code> then only the outgoing, if it is <code class="constant">IGRAPH_IN</code>
then only the incoming edges of a parent are considered. If it is
<code class="constant">IGRAPH_ALL</code> then all edges are used (this was the behavior in
igraph 0.5 and before). This parameter also influences how the root
vertices are calculated, if they are not given. See the <em class="parameter"><code>roots</code></em> parameter.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>roots</code></em>:</span></p></td>
<td><p>
The index of the root vertex or root vertices. The set of roots
should be specified so that all vertices of the graph are reachable from them.
Simply put, in the undirected case, one root should be given from each
connected component. If <em class="parameter"><code>roots</code></em> is <code class="constant">NULL</code> or a pointer to an empty vector,
then the roots will be selected automatically. Currently, automatic root
selection prefers low eccentricity vertices in graphs with fewer than
500 vertices, and high degree vertices (according to <em class="parameter"><code>mode</code></em>) in larger graphs.
The root selection heuristic may change without notice. To ensure a consistent
output, please specify the roots manually. The <a class="link" href="igraph-Layout.html#igraph_roots_for_tree_layout" title="2.3. igraph_roots_for_tree_layout — Roots suitable for a nice tree layout."><code class="function">igraph_roots_for_tree_layout()</code></a>
function gives more control over automatic root selection.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>rootlevel</code></em>:</span></p></td>
<td><p>
This argument can be useful when drawing forests which are
not trees (i.e. they are unconnected and have tree components). It specifies
the level of the root vertices for every tree in the forest. It is only
considered if not a null pointer and the <em class="parameter"><code>roots</code></em> argument is also given
(and it is not a null pointer of an empty vector).
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.2.
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_reingold_tilford_circular" title="2.2. igraph_layout_reingold_tilford_circular — Circular Reingold-Tilford layout for trees."><code class="function">igraph_layout_reingold_tilford_circular()</code></a>, <a class="link" href="igraph-Layout.html#igraph_roots_for_tree_layout" title="2.3. igraph_roots_for_tree_layout — Roots suitable for a nice tree layout."><code class="function">igraph_roots_for_tree_layout()</code></a>
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
<div class="hideshow" onClick="toggle(this, event)">
<div class="example">
<a name="id-1.30.3.2.13.1"></a><p class="title"><b>Example 29.1.  File <code class="code">examples/simple/igraph_layout_reingold_tilford.c</code></b></p>
<div class="example-contents">
<pre class="programlisting"><span class="strong"><strong>#include</strong></span> &lt;igraph.h&gt;
<span class="strong"><strong>#include</strong></span> &lt;math.h&gt;
int <span class="strong"><strong>main</strong></span>(void) {
igraph_t g;
FILE *f;
igraph_matrix_t coords;
<span class="emphasis"><em>/* Initialize the library. */</em></span>
<span class="strong"><strong><a class="link" href="igraph-Basic.html#igraph_setup" title="4.1. igraph_setup — Initializes the igraph library.">igraph_setup</a></strong></span>();
f = <span class="strong"><strong>fopen</strong></span>("igraph_layout_reingold_tilford.in", "r");
<span class="strong"><strong><a class="link" href="igraph-Foreign.html#igraph_read_graph_edgelist" title="1.1. igraph_read_graph_edgelist — Reads an edge list from a file and creates a graph.">igraph_read_graph_edgelist</a></strong></span>(&amp;g, f, 0, IGRAPH_DIRECTED);
<span class="strong"><strong>fclose</strong></span>(f);
<span class="strong"><strong><a class="link" href="igraph-Data-structures.html#igraph_matrix_init" title="3.2.1. igraph_matrix_init — Initializes a matrix.">igraph_matrix_init</a></strong></span>(&amp;coords, 0, 0);
<span class="strong"><strong><a class="link" href="igraph-Layout.html#igraph_layout_reingold_tilford" title="2.1. igraph_layout_reingold_tilford — Reingold-Tilford layout for tree graphs.">igraph_layout_reingold_tilford</a></strong></span>(&amp;g, &amp;coords, IGRAPH_IN, 0, 0);
<span class="strong"><strong>igraph_matrix_print</strong></span>(&amp;coords);
<span class="strong"><strong><a class="link" href="igraph-Data-structures.html#igraph_matrix_destroy" title="3.2.4. igraph_matrix_destroy — Destroys a matrix object.">igraph_matrix_destroy</a></strong></span>(&amp;coords);
<span class="strong"><strong><a class="link" href="igraph-Basic.html#igraph_destroy" title="5.1.4. igraph_destroy — Frees the memory allocated for a graph object.">igraph_destroy</a></strong></span>(&amp;g);
<span class="strong"><strong>return</strong></span> 0;
}
</pre>
<p></p>
</div>
</div>
<br class="example-break">
</div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_reingold_tilford_circular"></a>2.2. <code class="function">igraph_layout_reingold_tilford_circular</code> — Circular Reingold-Tilford layout for trees.</h3></div></div></div>
<a class="indexterm" name="id-1.30.3.3.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_reingold_tilford_circular(const igraph_t *graph,
igraph_matrix_t *res,
igraph_neimode_t mode,
const igraph_vector_int_t *roots,
const igraph_vector_int_t *rootlevel);
</pre></div>
<p>
</p>
<p>
This layout is almost the same as <a class="link" href="igraph-Layout.html#igraph_layout_reingold_tilford" title="2.1. igraph_layout_reingold_tilford — Reingold-Tilford layout for tree graphs."><code class="function">igraph_layout_reingold_tilford()</code></a>, but
the tree is drawn in a circular way, with the root vertex in the center.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
The result, the coordinates in a matrix. The parameter
should point to an initialized matrix object and will be resized.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>mode</code></em>:</span></p></td>
<td><p>
Specifies which edges to consider when building the tree.
If it is <code class="constant">IGRAPH_OUT</code> then only the outgoing, if it is <code class="constant">IGRAPH_IN</code>
then only the incoming edges of a parent are considered. If it is
<code class="constant">IGRAPH_ALL</code> then all edges are used (this was the behavior in
igraph 0.5 and before). This parameter also influences how the root
vertices are calculated, if they are not given. See the <em class="parameter"><code>roots</code></em> parameter.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>roots</code></em>:</span></p></td>
<td><p>
The index of the root vertex or root vertices. The set of roots
should be specified so that all vertices of the graph are reachable from them.
Simply put, in the undirected case, one root should be given from each
connected component. If <em class="parameter"><code>roots</code></em> is <code class="constant">NULL</code> or a pointer to an empty vector,
then the roots will be selected automatically. Currently, automatic root
selection prefers low eccentricity vertices in graphs with fewer than
500 vertices, and high degree vertices (according to <em class="parameter"><code>mode</code></em>) in larger graphs.
The root selection heuristic may change without notice. To ensure a consistent
output, please specify the roots manually.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>rootlevel</code></em>:</span></p></td>
<td><p>
This argument can be useful when drawing forests which are
not trees (i.e. they are unconnected and have tree components). It specifies
the level of the root vertices for every tree in the forest. It is only
considered if not a null pointer and the <em class="parameter"><code>roots</code></em> argument is also given
(and it is not a null pointer or an empty vector).
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_reingold_tilford" title="2.1. igraph_layout_reingold_tilford — Reingold-Tilford layout for tree graphs."><code class="function">igraph_layout_reingold_tilford()</code></a>.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_roots_for_tree_layout"></a>2.3. <code class="function">igraph_roots_for_tree_layout</code> — Roots suitable for a nice tree layout.</h3></div></div></div>
<a class="indexterm" name="id-1.30.3.4.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_roots_for_tree_layout(
const igraph_t *graph,
igraph_neimode_t mode,
igraph_vector_int_t *roots,
igraph_root_choice_t heuristic);
</pre></div>
<p>
</p>
<p>
This function chooses a root, or a set of roots suitable for visualizing a tree,
or a tree-like graph. It is typically used with <a class="link" href="igraph-Layout.html#igraph_layout_reingold_tilford" title="2.1. igraph_layout_reingold_tilford — Reingold-Tilford layout for tree graphs."><code class="function">igraph_layout_reingold_tilford()</code></a>.
The principle is to select a minimal set of roots so that all other vertices
will be reachable from them.
</p>
<p>
In the undirected case, one root is chosen from each connected component.
In the directed case, one root is chosen from each strongly connected component
that has no incoming (or outgoing) edges (depending on 'mode'). When more than
one root choice is possible, vertices are prioritized based on the given <em class="parameter"><code>heuristic</code></em>.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The graph, typically a tree, but any graph is accepted.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>mode</code></em>:</span></p></td>
<td><p>
Whether to interpret the input as undirected, a directed out-tree or in-tree.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>roots</code></em>:</span></p></td>
<td><p>
An initialized integer vector, the roots will be returned here.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>heuristic</code></em>:</span></p></td>
<td>
<p>
The heuristic to use for breaking ties when multiple root
choices are possible.
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_ROOT_CHOICE_DEGREE</code></span></p></td>
<td><p>
Choose the vertices with the highest degree (out- or in-degree
in directed mode). This simple heuristic is fast even in large graphs.
</p></td>
</tr>
<tr>
<td><p><span class="term"><code class="constant">IGRAPH_ROOT_CHOICE_ECCENTRICITY</code></span></p></td>
<td><p>
Choose the vertices with the lowest eccentricity. This usually results
in a "wide and shallow" tree layout. While this heuristic produces
high-quality results, it is slow for large graphs: computing the
eccentricities has quadratic complexity in the number of vertices.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
</td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: depends on the heuristic.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_sugiyama"></a>2.4. <code class="function">igraph_layout_sugiyama</code> — Sugiyama layout algorithm for layered directed acyclic graphs.</h3></div></div></div>
<a class="indexterm" name="id-1.30.3.5.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_sugiyama(
const igraph_t *graph, igraph_matrix_t *res, igraph_matrix_list_t *routing,
const igraph_vector_int_t* layers, igraph_real_t hgap, igraph_real_t vgap,
igraph_int_t maxiter, const igraph_vector_t *weights
);
</pre></div>
<p>
</p>
<p>
</p>
<p>
This layout algorithm is designed for directed acyclic graphs where each
vertex is assigned to a layer. Layers are indexed from zero, and vertices
of the same layer will be placed on the same horizontal line. The X coordinates
of vertices within each layer are decided by the heuristic proposed by
Sugiyama et al to minimize edge crossings.
</p>
<p>
You can also try to lay out undirected graphs, graphs containing cycles, or
graphs without an a priori layered assignment with this algorithm. igraph
will try to eliminate cycles and assign vertices to layers, but there is no
guarantee on the quality of the layout in such cases.
</p>
<p>
The Sugiyama layout may introduce "bends" on the edges in order to obtain a
visually more pleasing layout. The additional control points of the edges are
returned in a separate list of matrices, one matrix per edge in the original
graph. If an edge requires no additional control points, the corresponding
matrix will be empty, otherwise the matrix will contain the coordinates of
the control points, one point per row. When drawing the graph, edges should
be drawn in a way that the curve representing the edge passes through the
control points.
</p>
<p>
For more details, see K. Sugiyama, S. Tagawa and M. Toda, "Methods for Visual
Understanding of Hierarchical Systems". IEEE Transactions on Systems, Man and
Cybernetics 11(2):109-125, 1981.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will contain
the result and will be resized as needed. The coordinates of the
vertices in the layout will be stored in the rows of the matrix,
one row per vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>routing</code></em>:</span></p></td>
<td><p>
Pointer to an uninitialized list of matrices or <code class="constant">NULL</code>.
When not <code class="constant">NULL</code>, the list will be resized as needed such
that there will be one matrix for each edge of the graph,
and the matrix will hold the additional control points that
the edge must pass through, starting from the source vertex
of the edge and ending at the target vertex. The matrix will
have zero rows if an edge does not require control points.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>layers</code></em>:</span></p></td>
<td><p>
The layer index for each vertex or <code class="constant">NULL</code> if the layers should
be determined automatically by igraph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>hgap</code></em>:</span></p></td>
<td><p>
The preferred minimum horizontal gap between vertices in the same
layer.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>vgap</code></em>:</span></p></td>
<td><p>
The distance between layers.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxiter</code></em>:</span></p></td>
<td><p>
Maximum number of iterations in the crossing minimization stage.
100 is a reasonable default; if you feel that you have too
many edge crossings, increase this.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
Weights of the edges. These are used only if the graph contains
cycles; igraph will tend to reverse edges with smaller
weights when breaking the cycles.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_umap"></a>2.5. <code class="function">igraph_layout_umap</code> — Layout using Uniform Manifold Approximation and Projection (UMAP).</h3></div></div></div>
<a class="indexterm" name="id-1.30.3.6.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_umap(const igraph_t *graph,
igraph_matrix_t *res,
igraph_bool_t use_seed,
const igraph_vector_t *distances,
igraph_real_t min_dist,
igraph_int_t epochs,
igraph_bool_t distances_are_weights);
</pre></div>
<p>
</p>
<p>
</p>
<div class="warning" style="margin-left: 0.5in; margin-right: 0.5in;">
<h3 class="title">Warning</h3>
<p>This function is experimental and its signature is not considered final yet.
We reserve the right to change the function signature without changing the
major version of igraph. Use it at your own risk.</p>
</div>
<p>UMAP is mostly used to embed high-dimensional vectors in a low-dimensional space
(most commonly 2D). The algorithm is probabilistic and introduces nonlinearities,
unlike e.g. PCA and similar to T-distributed Stochastic Neighbor Embedding (t-SNE).
Nonlinearity helps "cluster" very similar vectors together without imposing a
global geometry on the embedded space (e.g. a rigid rotation + compression in PCA).
UMAP uses graphs as intermediate data structures, hence it can be used as a
graph layout algorithm as well.
</p>
<p>
The general UMAP workflow is to start from vectors, compute a sparse distance
graph that only contains edges between simiar points (e.g. a k-nearest neighbors
graph), and then convert these distances into exponentially decaying weights
between 0 and 1 that are larger for points that are closest neighbors in the
distance graph. If a graph without any distances associated to the edges is used,
all weights will be set to 1.
</p>
<p>
If you are trying to use this function to embed high-dimensional vectors, you should
first compute a k-nearest neighbors graph between your vectors and compute the
associated distances, and then call this function on that graph. If you already
have a distance graph, or you have a graph with no distances, you can call this
function directly. If you already have a graph with meaningful weights
associated to each edge, you can also call this function, but set the argument
<em class="parameter"><code>distances_are_weights</code></em> to true. To compute weights from distances
without computing the layout, see <a class="link" href="igraph-Layout.html#igraph_layout_umap_compute_weights" title="2.6. igraph_layout_umap_compute_weights — Compute weights for a UMAP layout starting from distances."><code class="function">igraph_layout_umap_compute_weights()</code></a>.
</p>
<p>
References:
</p>
<p>
Leland McInnes, John Healy, and James Melville:
UMAP: Uniform Manifold Approximation and Projection for Dimension Reduction (2020)
<a class="ulink" href="https://arxiv.org/abs/1802.03426" target="_top">https://arxiv.org/abs/1802.03426</a>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to the graph to find a layout for (i.e. to embed). This is
typically a sparse graph with only edges for the shortest distances stored, e.g.
a k-nearest neighbors graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to the n by 2 matrix where the layout coordinates will be stored.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
If <code class="constant">true</code> the supplied values in the <em class="parameter"><code>res</code></em> argument are
used as an initial layout, if <code class="constant">false</code> a random initial layout is used.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>distances</code></em>:</span></p></td>
<td><p>
Pointer to a vector of distances associated with the graph edges.
If this argument is <code class="constant">NULL</code>, all weights will be set to 1.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>min_dist</code></em>:</span></p></td>
<td><p>
A fudge parameter that decides how close two unconnected vertices
can be in the embedding before feeling a repulsive force. It must not be
negative. Typical values are between 0 and 1.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>epochs</code></em>:</span></p></td>
<td><p>
Number of iterations of the main stochastic gradient descent loop on
the cross-entropy. Typical values are between 30 and 500.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>distances_are_weights</code></em>:</span></p></td>
<td><p>
Whether to use precomputed weights. If
true, the <em class="parameter"><code>distances</code></em> vector contains precomputed weights. If <code class="constant">false</code> (the
typical use case), this function will compute weights from distances and
then use them to compute the layout.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_umap_3d" title="3.6. igraph_layout_umap_3d — 3D layout using UMAP."><code class="function">igraph_layout_umap_3d()</code></a>
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_umap_compute_weights"></a>2.6. <code class="function">igraph_layout_umap_compute_weights</code> — Compute weights for a UMAP layout starting from distances.</h3></div></div></div>
<a class="indexterm" name="id-1.30.3.7.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_umap_compute_weights(
const igraph_t *graph,
const igraph_vector_t *distances,
igraph_vector_t *weights);
</pre></div>
<p>
</p>
<p>
</p>
<div class="warning" style="margin-left: 0.5in; margin-right: 0.5in;">
<h3 class="title">Warning</h3>
<p>This function is experimental and its signature is not considered final yet.
We reserve the right to change the function signature without changing the
major version of igraph. Use it at your own risk.</p>
</div>
<p>UMAP is used to embed high-dimensional vectors in a low-dimensional space
(most commonly 2D). It uses a distance graph as an intermediate data structure,
making it also a useful graph layout algorithm. See <a class="link" href="igraph-Layout.html#igraph_layout_umap" title="2.5. igraph_layout_umap — Layout using Uniform Manifold Approximation and Projection (UMAP)."><code class="function">igraph_layout_umap()</code></a>
for more information.
</p>
<p>
An early step in UMAP is to compute exponentially decaying "weights" from the
distance graph. Connectivities can also be viewed as edge weights that quantify
similarity between two vertices. This function computes weights from the
distance graph. To compute the layout from precomputed weights, call
<a class="link" href="igraph-Layout.html#igraph_layout_umap" title="2.5. igraph_layout_umap — Layout using Uniform Manifold Approximation and Projection (UMAP)."><code class="function">igraph_layout_umap()</code></a> with the <em class="parameter"><code>distances_are_weights</code></em> argument set to <code class="constant">true</code>.
</p>
<p>
While the distance graph can be directed (e.g. in a k-nearest neighbors, it is
clear <span class="emphasis"><em>whom</em></span> you are a neighbor of), the weights are usually undirected. Whenever two
vertices are doubly connected in the distance graph, the resulting weight <code class="constant">W</code> is set as:
</p>
<p>
<code class="literal">W = W1 + W2 - W1 * W2</code>
Because UMAP weights are interpreted as probabilities, this is just the probability
that either edge is present, without double counting. It is called "fuzzy union" in
the original UMAP implementation and is the default. One could also require that both
edges are there, i.e. W = W1 * W2: this would represent the fuzzy intersection and is
not implemented in igraph. As a consequence of this symmetrization, information is lost,
i.e. one needs fewer weights than one had distances. To keep things efficient, here
we set the weight for one of the two edges as above and the weight for its opposite edge
as 0, so that it will be skipped in the UMAP gradient descent later on.
</p>
<p>
Technical note: For each vertex, this function computes its scale factor (sigma),
its connectivity correction (rho), and finally the weights themselves.
</p>
<p>
References:
</p>
<p>
Leland McInnes, John Healy, and James Melville:
UMAP: Uniform Manifold Approximation and Projection for Dimension Reduction (2020)
<a class="ulink" href="https://arxiv.org/abs/1802.03426" target="_top">https://arxiv.org/abs/1802.03426</a>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to the distance graph. This can be directed (e.g. connecting
each vertex to its neighbors in a k-nearest neighbor) or undirected, but must
have no loops nor parallel edges. The only exception is: if the graph is directed,
having pairs of edges with opposite direction is accepted.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>distances</code></em>:</span></p></td>
<td><p>
Pointer to the vector with the vertex-to-vertex distance associated with
each edge. This argument can be NULL, in which case all edges are assumed to have the
same distance.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
Pointer to an initialized vector where the result will be stored. If the
input graph is directed, the weights represent a symmetrized version which contains
less information. Therefore, whenever two edges between the same vertices and opposite
direction are present in the input graph, only one of the weights is set and the other
is fixed to zero. That format is accepted by <a class="link" href="igraph-Layout.html#igraph_layout_umap" title="2.5. igraph_layout_umap — Layout using Uniform Manifold Approximation and Projection (UMAP)."><code class="function">igraph_layout_umap()</code></a>, which skips
all zero-weight edges from the layout optimization.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_umap" title="2.5. igraph_layout_umap — Layout using Uniform Manifold Approximation and Projection (UMAP)."><code class="function">igraph_layout_umap()</code></a>, <a class="link" href="igraph-Layout.html#igraph_layout_umap_3d" title="3.6. igraph_layout_umap_3d — 3D layout using UMAP."><code class="function">igraph_layout_umap_3d()</code></a>
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
</div>
<div class="section">
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="three-d-layout-generators"></a>3. 3D layout generators</h2></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_random_3d">3.1. <code class="function">igraph_layout_random_3d</code> — Places the vertices uniformly randomly in a cube.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_sphere">3.2. <code class="function">igraph_layout_sphere</code> — Places vertices (more or less) uniformly on a sphere.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_grid_3d">3.3. <code class="function">igraph_layout_grid_3d</code> — Places the vertices on a regular grid in the 3D space.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_fruchterman_reingold_3d">3.4. <code class="function">igraph_layout_fruchterman_reingold_3d</code> — 3D Fruchterman-Reingold algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_kamada_kawai_3d">3.5. <code class="function">igraph_layout_kamada_kawai_3d</code> — 3D version of the Kamada-Kawai layout generator.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_umap_3d">3.6. <code class="function">igraph_layout_umap_3d</code> — 3D layout using UMAP.</a></span></dt>
</dl></div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_random_3d"></a>3.1. <code class="function">igraph_layout_random_3d</code> — Places the vertices uniformly randomly in a cube.</h3></div></div></div>
<a class="indexterm" name="id-1.30.4.2.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_random_3d(const igraph_t *graph, igraph_matrix_t *res);
</pre></div>
<p>
</p>
<p>
Vertex coordinates range from -1 to 1, and are placed in three columns
of a matrix, with a row for each vertex.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The graph to place.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. It will be
resized to hold the result.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.2.</p>
<p>
Time complexity: O(|V|), the number of vertices.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_sphere"></a>3.2. <code class="function">igraph_layout_sphere</code> — Places vertices (more or less) uniformly on a sphere.</h3></div></div></div>
<a class="indexterm" name="id-1.30.4.3.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_sphere(const igraph_t *graph, igraph_matrix_t *res);
</pre></div>
<p>
</p>
<p>
The vertices are placed with approximately equal spacing on a spiral
wrapped around a sphere, in the order of their vertex IDs. Vertices
with consecutive vertex IDs are placed near each other.
</p>
<p>
The algorithm was described in the following paper:
</p>
<p>
Distributing many points on a sphere by E.B. Saff and
A.B.J. Kuijlaars, <span class="emphasis"><em> Mathematical Intelligencer </em></span> 19.1 (1997)
5--11. <a class="ulink" href="https://doi.org/10.1007/BF03024331" target="_top">https://doi.org/10.1007/BF03024331</a>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code. The current implementation always returns with
success.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.2.</p>
<p>
Time complexity: O(|V|), the number of vertices in the graph.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_grid_3d"></a>3.3. <code class="function">igraph_layout_grid_3d</code> — Places the vertices on a regular grid in the 3D space.</h3></div></div></div>
<a class="indexterm" name="id-1.30.4.4.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_grid_3d(const igraph_t *graph, igraph_matrix_t *res,
igraph_int_t width, igraph_int_t height);
</pre></div>
<p>
</p>
<p>
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>width</code></em>:</span></p></td>
<td><p>
The number of vertices in a single row of the grid. When
zero or negative, the width is determined automatically.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>height</code></em>:</span></p></td>
<td><p>
The number of vertices in a single column of the grid. When
zero or negative, the height is determined automatically.</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code. The current implementation always returns with
success.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|), the number of vertices.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_fruchterman_reingold_3d"></a>3.4. <code class="function">igraph_layout_fruchterman_reingold_3d</code> — 3D Fruchterman-Reingold algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.4.5.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_fruchterman_reingold_3d(const igraph_t *graph,
igraph_matrix_t *res,
igraph_bool_t use_seed,
igraph_int_t niter,
igraph_real_t start_temp,
const igraph_vector_t *weights,
const igraph_vector_t *minx,
const igraph_vector_t *maxx,
const igraph_vector_t *miny,
const igraph_vector_t *maxy,
const igraph_vector_t *minz,
const igraph_vector_t *maxz);
</pre></div>
<p>
</p>
<p>
This is the 3D version of the force based Fruchterman-Reingold layout.
See <a class="link" href="igraph-Layout.html#igraph_layout_fruchterman_reingold" title="1.8. igraph_layout_fruchterman_reingold — Places the vertices on a plane according to the Fruchterman-Reingold algorithm."><code class="function">igraph_layout_fruchterman_reingold()</code></a> for the 2D version.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to an initialized graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result and will be resized as needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
If true the supplied values in the
<em class="parameter"><code>res</code></em> argument are used as an initial layout, if
false a random initial layout is used.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>niter</code></em>:</span></p></td>
<td><p>
The number of iterations to do. A reasonable
default value is 500.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>start_temp</code></em>:</span></p></td>
<td><p>
Start temperature. This is the maximum amount
of movement alloved along one axis, within one step, for a
vertex. Currently it is decreased linearly to zero during
the iteration.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
Pointer to a vector containing edge weights. Weights must
be positive. If <code class="constant">NULL</code>, all edges are assumed to have weight 1.
The attraction along the edges will be multiplied by the weights,
resulting in vertices connected by a high-weight edge being placed
closer together.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>minx</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">x</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxx</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>minx</code></em>, but the maximum <span class="quote"><span class="quote">x</span></span>
coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>miny</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">y</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxy</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>miny</code></em>, but the maximum <span class="quote"><span class="quote">y</span></span>
coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>minz</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">z</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxz</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>minz</code></em>, but the maximum <span class="quote"><span class="quote">z</span></span>
coordinates.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.2.</p>
<p>
Time complexity: O(|V|^2) in each
iteration, |V| is the number of
vertices in the graph.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_kamada_kawai_3d"></a>3.5. <code class="function">igraph_layout_kamada_kawai_3d</code> — 3D version of the Kamada-Kawai layout generator.</h3></div></div></div>
<a class="indexterm" name="id-1.30.4.6.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_kamada_kawai_3d(const igraph_t *graph, igraph_matrix_t *res,
igraph_bool_t use_seed, igraph_int_t maxiter,
igraph_real_t epsilon, igraph_real_t kkconst,
const igraph_vector_t *weights,
const igraph_vector_t *minx, const igraph_vector_t *maxx,
const igraph_vector_t *miny, const igraph_vector_t *maxy,
const igraph_vector_t *minz, const igraph_vector_t *maxz);
</pre></div>
<p>
</p>
<p>
This is the 3D version of <a class="link" href="igraph-Layout.html#igraph_layout_kamada_kawai" title="1.9. igraph_layout_kamada_kawai — Places the vertices on a plane according to the Kamada-Kawai algorithm."><code class="function">igraph_layout_kamada_kawai()</code></a>.
See the documentation of that function for more information.
</p>
<p>
This layout algorithm is not suitable for large graphs. The memory
requirements are of the order O(|V|^2).
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
A graph object.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object. This will
contain the result (x-, y- and z-positions in columns one
through three) and will be resized if needed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
Boolean, whether to use the values supplied in the
<em class="parameter"><code>res</code></em> argument as the initial configuration. If zero and there
are any limits on the z, y or z coordinates, then a random initial
configuration is used. Otherwise the vertices are placed uniformly
on a sphere of radius 1 as the initial configuration.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxiter</code></em>:</span></p></td>
<td><p>
The maximum number of iterations to perform. A reasonable
default value is at least ten (or more) times the number of
vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>epsilon</code></em>:</span></p></td>
<td><p>
Stop the iteration, if the maximum delta value of the
algorithm is smaller than this. It is safe to leave it at zero,
and then <em class="parameter"><code>maxiter</code></em> iterations are performed.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>kkconst</code></em>:</span></p></td>
<td><p>
The Kamada-Kawai vertex attraction constant.
Typical value: number of vertices.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>weights</code></em>:</span></p></td>
<td><p>
A vector of edge weights. Weights are interpreted as edge
<span class="emphasis"><em>lengths</em></span> in the shortest path calculation used by the
Kamada-Kawai algorithm. Therefore, vertices connected by high-weight
edges will be placed further apart. Pass <code class="constant">NULL</code> to assume unit weights
for all edges.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>minx</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">x</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxx</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>minx</code></em>, but the maximum <span class="quote"><span class="quote">x</span></span>
coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>miny</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">y</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxy</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>miny</code></em>, but the maximum <span class="quote"><span class="quote">y</span></span>
coordinates.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>minz</code></em>:</span></p></td>
<td><p>
Pointer to a vector, or a <code class="constant">NULL</code> pointer. If not a
<code class="constant">NULL</code> pointer then the vector gives the minimum
<span class="quote"><span class="quote">z</span></span> coordinate for every vertex.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>maxz</code></em>:</span></p></td>
<td><p>
Same as <em class="parameter"><code>minz</code></em>, but the maximum <span class="quote"><span class="quote">z</span></span>
coordinates.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|V|) for each iteration, after an O(|V|^2
log|V|) initialization step. |V| is the number of vertices in the
graph.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_umap_3d"></a>3.6. <code class="function">igraph_layout_umap_3d</code> — 3D layout using UMAP.</h3></div></div></div>
<a class="indexterm" name="id-1.30.4.7.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_umap_3d(const igraph_t *graph,
igraph_matrix_t *res,
igraph_bool_t use_seed,
const igraph_vector_t *distances,
igraph_real_t min_dist,
igraph_int_t epochs,
igraph_bool_t distances_are_weights);
</pre></div>
<p>
</p>
<p>
</p>
<div class="warning" style="margin-left: 0.5in; margin-right: 0.5in;">
<h3 class="title">Warning</h3>
<p>This function is experimental and its signature is not considered final yet.
We reserve the right to change the function signature without changing the
major version of igraph. Use it at your own risk.</p>
</div>
<p>This is the 3D version of the UMAP algorithm
(see <a class="link" href="igraph-Layout.html#igraph_layout_umap" title="2.5. igraph_layout_umap — Layout using Uniform Manifold Approximation and Projection (UMAP)."><code class="function">igraph_layout_umap()</code></a> for the 2D version).
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
Pointer to the graph to find a layout for (i.e. to embed). This is
typically a directed, sparse graph with only edges for the shortest distances
stored, e.g. a k-nearest neighbors graph with the edges going from each focal
vertex to its neighbors. However, it can also be an undirected graph. If the
<em class="parameter"><code>distances_are_weights</code></em> is <code class="constant">true</code>, this is treated as an undirected graph.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to the n by 3 matrix where the layout coordinates will be stored.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>use_seed</code></em>:</span></p></td>
<td><p>
If true the supplied values in the <em class="parameter"><code>res</code></em> argument are used
as an initial layout, if false a random initial layout is used.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>distances</code></em>:</span></p></td>
<td><p>
Pointer to a vector of distances associated with the graph edges.
If this argument is <code class="constant">NULL</code>, all edges are assumed to have the same distance.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>min_dist</code></em>:</span></p></td>
<td><p>
A fudge parameter that decides how close two unconnected vertices
can be in the embedding before feeling a repulsive force. It must not be
negative. Typical values are between 0 and 1.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>epochs</code></em>:</span></p></td>
<td><p>
Number of iterations of the main stochastic gradient descent loop on
the cross-entropy. Typical values are between 30 and 500.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>distances_are_weights</code></em>:</span></p></td>
<td><p>
Whether to use precomputed weights. If <code class="constant">false</code> (the
typical use case), this function will compute weights from distances and
then use them to compute the layout. If <code class="constant">true</code>, the <em class="parameter"><code>distances</code></em> vector contains
precomputed weights, including possibly some weights equal to zero that are
inconsequential for the layout optimization.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
<p><b>See also: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
<a class="link" href="igraph-Layout.html#igraph_layout_umap" title="2.5. igraph_layout_umap — Layout using Uniform Manifold Approximation and Projection (UMAP)."><code class="function">igraph_layout_umap()</code></a>
</p></td>
</tr></tbody>
</table></div>
<p>
</p>
</div>
</div>
<div class="section">
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="pp-layouts"></a>4. Post-processing layouts</h2></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_merge_dla">4.1. <code class="function">igraph_layout_merge_dla</code> — Merges multiple layouts by using a DLA algorithm.</a></span></dt>
<dt><span class="section"><a href="igraph-Layout.html#igraph_layout_align">4.2. <code class="function">igraph_layout_align</code> — Aligns a graph layout with the coordinate axes.</a></span></dt>
</dl></div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_merge_dla"></a>4.1. <code class="function">igraph_layout_merge_dla</code> — Merges multiple layouts by using a DLA algorithm.</h3></div></div></div>
<a class="indexterm" name="id-1.30.5.2.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_merge_dla(
const igraph_vector_ptr_t *thegraphs, const igraph_matrix_list_t *coords,
igraph_matrix_t *res
);
</pre></div>
<p>
</p>
<p>
First each layout is covered by a circle. Then the layout of the
largest graph is placed at the origin. Then the other layouts are
placed by the DLA algorithm, larger ones first and smaller ones
last.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>thegraphs</code></em>:</span></p></td>
<td><p>
Pointer vector containing the graph objects of
which the layouts will be merged.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>coords</code></em>:</span></p></td>
<td><p>
List of matrices with the 2D layouts of the graphs in <em class="parameter"><code>thegraphs</code></em>.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>res</code></em>:</span></p></td>
<td><p>
Pointer to an initialized matrix object, the result will
be stored here. It will be resized if needed.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Added in version 0.2.
</p>
<p>
Time complexity: TODO.
</p>
</div>
<div class="section">
<div class="titlepage"><div><div><h3 class="title">
<a name="igraph_layout_align"></a>4.2. <code class="function">igraph_layout_align</code> — Aligns a graph layout with the coordinate axes.</h3></div></div></div>
<a class="indexterm" name="id-1.30.5.3.2"></a><p>
</p>
<div class="informalexample"><pre class="programlisting">
igraph_error_t igraph_layout_align(const igraph_t *graph, igraph_matrix_t *layout);
</pre></div>
<p>
</p>
<p>
This function centers a vertex layout on the coordinate system origin and
rotates the layout to achieve a visually pleasing alignment with the coordinate
axes. Doing this is particularly useful with force-directed layouts such as
<a class="link" href="igraph-Layout.html#igraph_layout_fruchterman_reingold" title="1.8. igraph_layout_fruchterman_reingold — Places the vertices on a plane according to the Fruchterman-Reingold algorithm."><code class="function">igraph_layout_fruchterman_reingold()</code></a>. Layouts in arbitrary dimensional
spaces are supported.
</p>
<p><b>Arguments: </b>
</p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody>
<tr>
<td><p><span class="term"><em class="parameter"><code>graph</code></em>:</span></p></td>
<td><p>
The graph whose layout is to be aligned.
</p></td>
</tr>
<tr>
<td><p><span class="term"><em class="parameter"><code>layout</code></em>:</span></p></td>
<td><p>
A matrix whose rows are the coordinates of vertices. It will
be modified in-place.
</p></td>
</tr>
</tbody>
</table></div>
<p>
</p>
<p><b>Returns: </b></p>
<div class="variablelist"><table border="0" class="variablelist">
<colgroup>
<col align="left" valign="top">
<col>
</colgroup>
<tbody><tr>
<td><p><span class="term"><em class="parameter"><code></code></em></span></p></td>
<td><p>
Error code.
</p></td>
</tr></tbody>
</table></div>
<p>
Time complexity: O(|E| + |V|), linear in the number of edges and vertices.
</p>
</div>
</div>
</div>
<table class="navigation-footer" width="100%" summary="Navigation footer" cellpadding="2" cellspacing="0"><tr valign="middle">
<td align="left"><a accesskey="p" href="igraph-Embedding.html"><b>← Chapter 28. Embedding of graphs</b></a></td>
<td align="right"><a accesskey="n" href="igraph-Processes.html"><b>Chapter 30. Processes on graphs →</b></a></td>
</tr></table>
</body>
</html>