Лекция 1.6. Графвиз — различия между версиями

Материал из Wiki
Перейти к:навигация, поиск
 
(не показаны 102 промежуточные версии 4 участников)
Строка 1: Строка 1:
'''Graphviz''' — это разработанный специалистами лаборатории AT&T пакет утилит по автоматической визуализации графов, заданных в виде текстового описания. Пакет распространяется с открытыми исходными файлами и работает на всех операционных системах, включая Windows, Linux/Unix, Mac OS. Самой интересной программой пакета является «dot», автоматический визуализатор направленных графов, который принимает на вход текстовый файл со структурой графа, а на выходе формирует граф в виде графического, векторного или текстового файла.
+
'''Graphviz''' - набор утилит для графического представления данных.
+
Программа  принимает описания отношений и элементов множеств, на которых определяется граф, и "добавляет" к этим лишенным всяких геометрических атрибутов описаниям дополнительную информацию, позволяющую "нарисовать" картинку графа.
= Быстрый старт =
 
  
Входной файл для программы «DOT» является обычным текстовым файлом на специальном языке разметки графа. Структура файла очень простая, например,
+
Для использования Графвиз требуется использовать примитивный язык описания графов dgl.
 +
Основные понятия:
 +
* граф,
 +
* вершина графа -- элемент множества,  
 +
* ребро графа, соединяющее вершину N с вершиной M
  
digraph G{
+
== Быстрый старт ==
  Рождение->Юность->Зрелость->Старость->Смерть;
 
  Юность->Смерть;
 
  Зрелость->Смерть;
 
}
 
  
на выходе будет
+
Входной файл для программы «DOT» является обычным текстовым файлом на специальном языке разметки графа. Структура файла очень простая, например,
  
<graph>  
+
<nowiki> <graphviz>  
 
  digraph G{
 
  digraph G{
      Рождение->Юность->Зрелость->Старость->Смерть;
+
Рождение->Юность->Зрелость->Старость->Смерть;
      Юность->Смерть;
+
Юность->Смерть;
      Зрелость->Смерть;
+
  Зрелость->Смерть;
  }
 
</graph>
 
 
 
Программа «Dot» сама распознает все связи графа и упорядочит его таким образом, чтобы было наименьшее количество пересечений.
 
 
 
Чтобы использовать «dot»-графы в [[{{SITENAME}}]], используйте следующий синтаксис:
 
 
 
  <nowiki><graph>
 
digraph G{
 
  Рождение->Юность->Зрелость->Старость->Смерть;
 
  Юность->Смерть;
 
  Зрелость->Смерть;
 
 
  }
 
  }
  </graph></nowiki>
+
  </graphviz></nowiki>
  
Если у вас узлы поименованы словосочетаниями, заключите их в кавычки, т. е.
+
на выходе будет:
  
<nowiki><graph>
+
<graphviz>  
 
digraph G{
 
digraph G{
  "Полет фантазии"->"Расход горючего";
+
Рождение->Юность->Зрелость->Старость->Смерть;
}
+
Юность->Смерть;
</graph></nowiki>
+
Зрелость->Смерть;
 +
}
 +
</graphviz>
  
Поздравляем! Теперь вы способны рисовать графы в [[{{SITENAME}}]]. Остальной текст будет посвящен некоторым тонкостям использования [[Graphviz]].
+
Программа «Dot» сама распознает все связи графа и упорядочит его таким образом, чтобы было наименьшее количество пересечений.
  
= Внешний вид графа =
+
Если у вас узлы поименованы словосочетаниями, заключите их в кавычки, например:
«Dot» позволяет изменять внешний вид графа. Например, можно изменять форму фигур (прямоугольники, овалы, круги, параллелограммы, многоугольники), цвет и шрифт текста, цвет фона фигур, стиль стрелок и рамок фигур, подписи стрелок и т. д.
 
Итак, основные объектами являются узлы («node») и ребра («edge»). Для того, чтобы настроить свойства всех узлов или ребер нужно вначале использовать команды
 
node[свойство1="значение1",свойство2="значение2",...]
 
edge[свойство1="значение1",свойство2="значение2",...]
 
Также (в квадратных скобках после описания объекта) можно изменять настройки конкретного узла или ребра. Параметры графа, просто задаются в виде <tt>параметр=значение</tt>.
 
Полезно запомнить параметр «rankdir», он может быть «TB» (top->bottom, параметр по умолчанию), или «LR» (left->right), и определяет, сверху-вниз, или справа-налево, нужно располагать узлы графа. Вот пестрый пример:
 
  
 +
<nowiki> <graphviz>
 
  digraph G{
 
  digraph G{
  rankdir=LR;
+
"Сидоров Пётр Фёдорович" -> "Сидоров Иван Петрович" [label="отец"];
  node[color="red",fontsize=14];
+
"Сидорова Анна Павловна " -> "Сидоров Иван Петрович" [label="мать"];
  edge[color="darkgreen",fontcolor="blue",fontsize=12];
+
  }  
  OPEN[shape="rectangle",style="filled",fillcolor="lightgrey"];
+
</graphviz></nowiki>
  CLOSED[shape="octagon",label="Финиш"];
 
  VERIFIED[shape="rectangle",style="rounded"];
 
  OPEN->RESOLVED->VERIFIED->CLOSED;
 
  OPEN->CLOSED[style="bold"];
 
  VERIFIED->OPEN[label="обнаружены ошибки",style="dashed",arrowhead="dot"];
 
  }
 
  
на выходе будет
+
<graphviz>
 
 
<graph>
 
digraph G{
 
  rankdir=LR;
 
  node[color="red",fontsize=14];
 
  edge[color="darkgreen",fontcolor="blue",fontsize=12];
 
  OPEN[shape="rectangle",style="filled",fillcolor="lightgrey"];
 
  CLOSED[shape="octagon",label="Финиш"];
 
  VERIFIED[shape="rectangle",style="rounded"];
 
  OPEN->RESOLVED->VERIFIED->CLOSED;
 
  OPEN->CLOSED[style="bold"];
 
  VERIFIED->OPEN[label="обнаружены ошибки",style="dashed",arrowhead="dot"];
 
}
 
</graph>
 
 
 
Если предполагается, что граф будут не только просматривать через IE, но и печатать, то необходимо установить ширину картинки, иначе при печати картинка будет обрезана. Для этого следует задать внутри описания
 
size="6.7,15";
 
Существенна только первая цифра. Число 6.7 подобрано эмпирически, оно обеспечивает печать полной картинки при настройках IE по умолчанию.
 
 
 
= Уровни в графах =
 
 
 
В «Dot» присутствует возможность связать узлы графа не только стрелками, но и уровнями отображения, что позволяет создавать шкалу и располагать узлы графа соответственно данной шкале. Для связывания используется следующая конструкция:
 
  { rank = same; "элемент уровня"; "элемент для привязки 1"; "элемент для привязки 2"; ..}
 
 
 
 
Например, при использовании следующей конструкции:
 
<nowiki><graph>
 
 
  digraph G{
 
  digraph G{
  node[fontsize=9];
+
  "Сидоров Пётр Фёдорович" -> "Сидоров Иван Петрович" [label="отец"];
  { /* шкала месяцев*/
+
  "Сидорова Анна Павловна " -> "Сидоров Иван Петрович" [label="мать"];
    node[shape=plaintext]; /* что бы не было видно рамок */
+
}  
    edge[color=white] /* что бы не было видно стрелок */
+
  </graphviz>
    "март" -> "июнь" -> "сентябрь" -> "декабрь";
 
  }
 
  { rank = same; "март"; "весна"; "a"; }
 
  { rank = same; "июнь"; "лето";}
 
  { rank = same; "сентябрь"; "осень"; "d"; }
 
  { rank = same; "декабрь"; "зима"; "e"}
 
  "весна" -> "лето" -> "осень" -> "зима" -> "весна"
 
  "a" -> "b" -> "c" -> "d" -> "e" ;
 
}
 
</graph></nowiki>
 
 
 
на выходе получается:
 
<graph>
 
digraph G{
 
  node[fontsize=9];
 
  { /* шкала месяцев*/
 
    node[shape=plaintext]; /* что бы не было видно рамок */
 
    edge[color=white] /* что бы не было видно стрелок */
 
    "март" -> "июнь" -> "сентябрь" -> "декабрь";
 
  }
 
  { rank = same; "март"; "весна"; "a"; }
 
  { rank = same; "июнь"; "лето";}
 
  { rank = same; "сентябрь"; "осень"; "d"; }
 
  { rank = same; "декабрь"; "зима"; "e"}
 
  "весна" -> "лето" -> "осень" -> "зима" -> "весна"
 
  "a" -> "b" -> "c" -> "d" -> "e" ;
 
  }
 
</graph>
 
  
= Многосекционный узлы =
+
==Свойства графа==
  
Dot позволяет создавать многосекционные узлы при это каждая секция может быть поименована, и тогда ребра можно продоводить между секциями и узлами.
+
Для того, граф было удобнее просматривать, можно настроить следующие  свойства. Например:
 +
* Направленность графа:
 +
**'''rankdir=LR''' - слева-направо
 +
**'''rankdir=TB''' - сверху вниз
 +
**'''ratio=auto''' - отношение = авто;
 +
*'''Цвет фона графа''' - graph [bgcolor=Snow2] - окрашивает фон в цвет - "серый снег"
 +
* '''Свойства''' (node) '''узлов''' - node[color="Pink",fontsize=10, style=filled, fontcolor="blue",  shape="none"] (Сочетание двух и более слов записывается в кавычки - '''"Нижний Новгород"''')
 +
** '''color="Pink"''' - цвет = розовый ([[Цвета в Вики]])
 +
** '''fontsize=8''' - размер шрифта = 8
 +
** '''style=filled''' - стиль = заполненный (без неё узел прозрачен)
 +
** '''fontcolor="blue"''' - цвет шрифта = голубой
 +
** '''shape="none"''' - форма = "без формы"
 +
*** '''Формы узла [shape=?]''' - '''invtriangle''' - треугольник вершиной вниз; '''box''' - прямоугольник; '''ellipse''' - эллипс; '''invtrapezium''' - перевёрнутая трапеция; '''triangle''' - треугольник;  '''trapezium''' - трапеция; '''octagon''' - восьмиугольник; '''tripleoctagon''' - тройной восьмиугольник ([http://www.graphviz.org/doc/info/shapes.html Все формы])
 +
** '''Ярославль [shape=Mdiamond]''' - узлу Ярославль придаётся форма ромба(алмаз)
 +
** '''Сызрань [shape=Msquare]''' - узлу Сызрань придаётся форма квадрата
 +
** '''Кострома [shape=circle]''' - узлу Кострома придаётся форма круга
 +
** '''"Нижний Новгород" [shape=doublecircle]''' - узлу "Нижний Новгород" придаётся форма двойного круга
 +
** '''Казань [shape=hexagon,color=green]''' - узлу Казань придаётся форма шестиугольника и зелёный цвет
 +
* Управление положением узлов - '''{rank=same; Елабуга Дзержинск Сызрань ;}''' - узлам Елабуга, Дзержинск, Сызрань предан  разряд = тот же самый;  '''ranksep=3''' - расстояние между разрядами;
 +
* '''Свойства''' (edge) '''ребер''' - edge[color="blue",fontcolor="Green",fontsize=12]
 +
** '''color="Brown"''' - цвет = коричневый
 +
*** '''color="Green:blue:red"''' - трёхцветие (возможно любое количество)
 +
**  '''dir=both''' - направление стрелки в две стороны
 +
** '''fontsize=8''' - размер шрифта = 8
 +
** '''fontcolor="blue"''' - цвет шрифта = зелёный
 +
** '''style=dotted''' - стиль = пунктирная линия
 +
** '''arrowhead="dot"''' - голова стрелки = "точка", "none" - нет ([http://www.graphviz.org/doc/info/arrows.html Все формы])
 +
* '''Ярлык ребра''' [label="Волга"] - все связи  '''Ярославль -> ... -> Сызрань'''  будут помечены меткой Волга.
  
Для включения режима многосекционности устанавливается атрибут узла shape.
 
shape=record;
 
  
Секции описываются в атрибуте label узла,  с помощью разделителя «|». Для именования секции ее имя указывается в <>. При описание ребра, исходящего или входящего в секцию, секция именуется следующим образом:
 
  
элемент:<имя_секции>
+
'''''Пример:'''''
  
Например, из такого описания:
+
<nowiki><graphviz>
 
+
  digraph G{
  digraph structs {
+
graph [bgcolor=Snow2];
  rankdir=HR;
+
rankdir=LR ; // направление графа слева направо
  first [shape=record,label="  x1\n all | { x21 | <f0> x22| x23} | x3" ];
+
node[color="Pink",fontsize=8, fontcolor="blue",style=filled, shape="none"] ;
  second [shape=record,label=" x22_1 | x22_2 | x22_3"];
+
edge[color="Brown",fontcolor="Green",fontsize=8] ;
  first:<f0> -> second;
+
  Ярославль -> Кострома -> "Нижний Новгород" -> Казань -> Сызрань [dir=both, label="Волга"];
 +
"Нижний Новгород" -> Дзержинск [style=dotted, label="Ока",arrowhead="dot" ] ;
 +
Казань -> Елабуга [label="Кама", color="Green:blue:red"] ;
 +
Ярославль [shape=Mdiamond], Сызрань [shape=Msquare], Кострома [shape=circle];
 +
"Нижний Новгород" [shape = doublecircle],Казань[shape=hexagon,color=green]
 +
{rank=same; Елабуга Дзержинск Сызрань ;}
 
  }
 
  }
 +
</graphviz></nowiki>
  
Получается следующее:
+
'''''Результат:'''''
  
<graph>
+
<graphviz>
  digraph structs {
+
  digraph G{
  rankdir=HR;
+
graph [bgcolor=Snow2];
  first [shape=record,label=" x1\n all | { x21 | <f0> x22| x23} | x3" ];
+
rankdir=LR ;  
  second [shape=record,label=" x22_1 | x22_2 | x22_3"];
+
node[color="Pink",fontsize=8, fontcolor="blue",style=filled, shape="none"] ;
  first:<f0> -> second;
+
edge[color="Brown",fontcolor="Green",fontsize=8] ;
}
+
Ярославль -> Кострома -> "Нижний Новгород" -> Казань -> Сызрань [dir=both, label="Волга"];
</graph>
+
"Нижний Новгород" -> Дзержинск [style=dotted, label="Ока",arrowhead="dot" ] ;
 
+
  Казань -> Елабуга [label="Кама", color="Green:blue:red"] ;
= Гиперссылки на графах =
+
Ярославль [shape=Mdiamond], Сызрань [shape=Msquare], Кострома [shape=circle];
 
+
"Нижний Новгород" [shape = doublecircle],Казань[shape=hexagon,color=green]
Можно использовать атрибут «URL», задавая относительные или абсолютные гиперссылки для узлов и ребер. Например
+
{rank=same; Елабуга Дзержинск Сызрань ;}
 
 
<nowiki><graph>
 
digraph G {
 
    rankdir=LR;
 
            SGML [URL="SGML"];
 
            HTML [URL="HTML"];
 
            XML [URL="XML"];
 
            XHTML [URL="http://www.w3schools.com/xhtml/"];
 
    SGML->HTML;
 
    SGML->XML;
 
    HTML->XHTML;
 
    XML->XHTML;
 
    SGML->XHTML[color="red",fontcolor="blue",label="ссылка на Google",URL="http://www.google.com"];
 
  }
 
</graph></nowiki>
 
 
 
 
 
<graph>
 
digraph G {
 
    rankdir=LR;
 
            SGML [URL="SGML"];
 
            HTML [URL="HTML"];
 
            XML [URL="XML"];
 
            XHTML [URL="http://www.w3schools.com/xhtml/"];
 
    SGML->HTML;
 
    SGML->XML;
 
    HTML->XHTML;
 
    XML->XHTML;
 
    SGML->XHTML[color="red",fontcolor="blue",label="ссылка на Google",URL="http://www.google.com"];
 
 
}
 
}
</graph>
+
  </graphviz>
 
 
= Кластеры в графах =
 
 
 
Программа «Dot» позволяет объединять узлы графов в кластеры для подчеркивания общности.
 
 
 
Кластер описывается следующим синтаксисом:
 
subgraph имя{
 
свойство1 = "значение1",свойство2="значение2",...
 
узел1;
 
узел2;
 
...
 
}
 
При этом ''имя'' подграфа должно начинаться с префикса '''cluster''', иначе подграф не позволяет себя отобразить на экран(раскраска, контур, подпись, .. ).
 
 
 
Например:
 
 
 
  digraph G {
 
  rankdir=LR;
 
  subgraph cluster0 {
 
        node [style=filled,color=white];
 
        style=filled;
 
        color=lightgrey;
 
        a0;
 
        a1
 
        label = "process #1";
 
  }
 
  subgraph cluster1 {
 
        node [style=filled];
 
        b0;
 
        label = "process #2";
 
        color=blue
 
  }
 
  start -> a0;
 
  start -> b0;
 
  a0 -> a1 -> end;
 
  b0 -> end;
 
  }
 
 
 
<graph>
 
digraph G {
 
  rankdir=LR;
 
  subgraph cluster0 {
 
        node [style=filled,color=white];
 
        style=filled;
 
        color=lightgrey;
 
        a0;
 
        a1
 
        label = "process #1";
 
  }
 
  subgraph cluster1 {
 
        node [style=filled];
 
        b0;
 
        label = "process #2";
 
        color=blue
 
  }
 
  start -> a0;
 
  start -> b0;
 
  a0 -> a1 -> end;
 
  b0 -> end;
 
  }
 
</graph>
 
 
 
= Цвета и черно-белая печать=
 
Graphviz позволяет использовать широкую цветовую палитру, однако, стоит не забывать, что контрастно выглядящие на цветном мониторе цвета, могут быть совершенно неразличимы после черно-белой печати. После проделанных экспериментов ({{Bug|11015}}), можно рекомендовать следующие палитры цветов (иллюстрированы на цвете ребер графа):
 
 
 
<graph-print>
 
digraph G{ rankdir=TB; size="7,6";
 
 
 
Палитра1->goldenrod1 [color=goldenrod1]
 
Палитра1->green [color=green]
 
Палитра1->sienna4 [color=sienna4]
 
Палитра1->red1 [color=red1]
 
Палитра1->blue2 [color=blue2]
 
 
 
Палитра2->lightcyan2 [color=lightcyan2]
 
Палитра2->pink2 [color=pink2]
 
Палитра2->green [color=green]
 
Палитра2->sienna4 [color=sienna4]
 
Палитра2->red2 [color=red2]
 
Палитра2->black1 [color=black1]
 
}
 
</graph-print>
 
 
 
= Формы вершин =
 
 
 
Перечислим палитру возможных форм вершин (узлов).
 
 
 
<neato>
 
digraph G{ 
 
edge [arrowtail="none"]
 
node [style=filled,  colorscheme="brbg9"];
 
 
"box"      [shape="box"      fillcolor="1"];
 
"polygon"  [shape="polygon"      fillcolor="2"];
 
"ellipse"  [shape="ellipse"      fillcolor="3"];
 
"circle"  [shape="circle"      fillcolor="4"];
 
"point"  [shape="point"      fillcolor="black"];
 
"egg"  [shape="egg"      fillcolor="6"];
 
"triangle"  [shape="triangle"      fillcolor="7"];
 
"plaintext"  [shape="plaintext"      fillcolor="8"];
 
"diamond"  [shape="diamond"      fillcolor="9"];
 
"trapezium"  [shape="trapezium"      fillcolor="1"];
 
"parallelogram"  [shape="parallelogram"      fillcolor="2"];
 
"house"  [shape="house"      fillcolor="3"];
 
  "pentagon"  [shape="pentagon"      fillcolor="4"];
 
"hexagon"  [shape="hexagon"      fillcolor="5"];
 
"septagon"  [shape="septagon"      fillcolor="6"];
 
"octagon"  [shape="octagon"      fillcolor="7"];
 
"doublecircle"  [shape="doublecircle"      fillcolor="8"];
 
"doubleoctagon"  [shape="doubleoctagon"      fillcolor="9"];
 
"tripleoctagon"  [shape="tripleoctagon"      fillcolor="1"];
 
"invtriangle"  [shape="invtriangle"      fillcolor="1"];
 
"invtrapezium"  [shape="invtrapezium"      fillcolor="2"];
 
"invhouse"  [shape="invhouse"      fillcolor="3"];
 
"Mdiamond"  [shape="Mdiamond"      fillcolor="4"];
 
"Msquare"  [shape="Msquare"      fillcolor="5"];
 
"Mcircle"  [shape="Mcircle"      fillcolor="6"];
 
"rect/rectangle"  [shape="rect"      fillcolor="7"];
 
"none"  [shape="none"      fillcolor="8"];
 
"note"  [shape="note"      fillcolor="9"];
 
"tab"  [shape="tab"      fillcolor="1"];
 
"folder"  [shape="folder"      fillcolor="2"];
 
"box3d"  [shape="box3d"      fillcolor="3"];
 
"component"  [shape="component"      fillcolor="4"];
 
}
 
</neato>
 
 
 
= Окончания ребер =
 
Можно задавать стиль офомления начала («arrowtail») и конца («arrowhead») дуг (ребер):
 
 
 
<circo>
 
digraph G{ 
 
 
 
edge [arrowtail="none"]
 
A [label="Arrowhead" style=filled fillcolor="yellow"];
 
 
  A->"normal" [arrowhead="normal"];
 
  A->"dot" [arrowhead="dot"];
 
  A->"odot" [arrowhead="odot"];
 
  A->"none" [arrowhead="none"];
 
  A->"empty" [arrowhead="empty"];
 
  A->"diamond" [arrowhead="diamond"];
 
  A->"ediamond" [arrowhead="ediamond"];
 
  A->"box" [arrowhead="box"];
 
  A->"open" [arrowhead="open"];
 
  A->"vee" [arrowhead="vee"];
 
  A->"inv" [arrowhead="inv"];
 
  A->"invdot" [arrowhead="invdot"];
 
  A->"invodot" [arrowhead="invodot"];
 
  A->"tee" [arrowhead="tee"];
 
  A->"invempty" [arrowhead="invempty"];
 
  A->"odiamond" [arrowhead="odiamond"];
 
  A->"crow" [arrowhead="crow"];
 
  A->"obox" [arrowhead="obox"];
 
  A->"halfopen" [arrowhead="halfopen"];
 
}
 
</circo>
 
 
 
= Неориентированные графы =
 
Наряду с рисованием ориентированных графов, есть несколько методов для автоматического рисования неориентированных графов (будем рассматривать их на примере несложной ER-диаграммы).
 
 
 
В отличие от автоматического рисования направленных («directed») графов, основанных на ранговой модели, есть несколько подходов к раскладке ненаправленных графов.
 
 
 
== Graph ==
 
Ненаправленный граф можно нарисовать с помощью рангового подхода (несмотря на ненаправленность ребер) — будет использоваться программа «dot». Как это будет выглядеть для простой ER-диаграммы, можно увидеть ниже.
 
<graph>
 
graph ER
 
{
 
  node [fontsize=12];
 
  node [shape=box]; course; institute; student;
 
  node [shape=ellipse];
 
  {node [label="name"] name0; name1; name2;}
 
  code; grade; number;
 
node [shape=diamond,style=filled,color=lightgrey];
 
  "C-I"; "S-C"; "S-I";
 
name0 -- course;
 
code -- course;
 
course -- "C-I" [label="n",len=1.00];
 
"C-I" -- institute [label="1",len=1.00];
 
institute -- name1;
 
institute -- "S-I" [label="1",len=1.00];
 
"S-I" -- student [label="n",len=1.00];
 
student -- grade;
 
student -- name2;
 
student -- number;
 
student -- "S-C" [label="m",len=1.00];
 
"S-C" -- course [label="n",len=1.00];
 
  label = "\n\nEntity Relation Diagram\ndrawn by DOT";
 
}
 
</graph>
 
 
 
Очевидна неоптимальность такого подхода для неориентированных графов.
 
 
 
== Neato ==
 
 
 
Метод «neato» использует «энергетическую» (''spring'') модель, по сути, близкую к методу искуственного отжига — начиная с некоторого состояния вершины перемещаются, чтобы минимизировать некую потенциальную энергию. Рекомендуем для ненаправленных графов общего вида.
 
 
 
<neato>
 
graph ER
 
{
 
node [fontsize=12];
 
node [shape=box]; course; institute; student;
 
  node [shape=ellipse];
 
  {node [label="name"] name0; name1; name2;}
 
  code; grade; number;
 
node [shape=diamond,style=filled,color=lightgrey];
 
  "C-I"; "S-C"; "S-I";
 
name0 -- course;
 
code -- course;
 
course -- "C-I" [label="n",len=1.00];
 
"C-I" -- institute [label="1",len=1.00];
 
  institute -- name1;
 
  institute -- "S-I" [label="1",len=1.00];
 
"S-I" -- student [label="n",len=1.00];
 
student -- grade;
 
student -- name2;
 
student -- number;
 
student -- "S-C" [label="m",len=1.00];
 
"S-C" -- course [label="n",len=1.00];
 
label = "\n\nEntity Relation Diagram\ndrawn by NEATO";
 
}
 
</neato>
 
 
 
== FDP ==
 
Метод «fdp» по сути, близок к методу «neato», и использует другую разновидность «энергетического» («spring») подхода. Также рекомендуется для ненаправленных графов общего типа.
 
 
 
<fdp>
 
graph ER
 
{
 
node [fontsize=12];
 
node [shape=box]; course; institute; student;
 
  node [shape=ellipse];
 
  {node [label="name"] name0; name1; name2;}
 
  code; grade; number;
 
node [shape=diamond,style=filled,color=lightgrey];
 
  "C-I"; "S-C"; "S-I";
 
name0 -- course;
 
code -- course;
 
course -- "C-I" [label="n",len=1.00];
 
"C-I" -- institute [label="1",len=1.00];
 
  institute -- name1;
 
institute -- "S-I" [label="1",len=1.00];
 
"S-I" -- student [label="n",len=1.00];
 
student -- grade;
 
student -- name2;
 
student -- number;
 
student -- "S-C" [label="m",len=1.00];
 
"S-C" -- course [label="n",len=1.00];
 
label = "\n\nEntity Relation Diagram\ndrawn by FDP";
 
}
 
</fdp>
 
 
 
 
 
 
 
 
 
== Twopi ==
 
 
 
Метод «twopi» рисует графы с радиальной раскладкой. По сути одна вершина выбирается центральной, и помещается в центр, а остальные размещаются на последовательности концентрических орбит, вокруг этой вершины. Т.е. все вершины на расстоянии в «одно ребро» от центра, лежат на первой орбите, «в два ребра» — на второй и т. д.
 
 
 
<twopi>
 
graph ER
 
{
 
 
node [fontsize=12];
 
  node [shape=box]; course; institute; student;
 
  node [shape=ellipse];
 
  {node [label="name"] name0; name1; name2;}
 
  code; grade; number;
 
node [shape=diamond,style=filled,color=lightgrey];
 
  "C-I"; "S-C"; "S-I";
 
name0 -- course;
 
code -- course;
 
course -- "C-I" [label="n",len=1.00];
 
"C-I" -- institute [label="1",len=1.00];
 
  institute -- name1;
 
institute -- "S-I" [label="1",len=1.00];
 
"S-I" -- student [label="n",len=1.00];
 
student -- grade;
 
student -- name2;
 
student -- number;
 
student -- "S-C" [label="m",len=1.00];
 
"S-C" -- course [label="n",len=1.00];
 
label = "\n\nEntity Relation Diagram\ndrawn by TWOPI";
 
}
 
</twopi>
 
 
 
== CIRCO ==
 
 
 
Метод «circo» использует «circular layout». Выделяются двусвязные компоненты (каждая вершина имеет по крайней мере два ребра) и вершины этих компонент рисуются на некотором круге. «Дополнительные» ребра рисуются радиально и далее процесс повторяется. Пересечение ребер внутри круга минимизируется максимально возможным выносом ребер с круга за его периметр.
 
 
 
<circo>
 
graph ER
 
{
 
node [fontsize=12];
 
node [shape=box]; course; institute; student;
 
  node [shape=ellipse];
 
  {node [label="name"] name0; name1; name2;}
 
  code; grade; number;
 
node [shape=diamond,style=filled,color=lightgrey];
 
  "C-I"; "S-C"; "S-I";
 
name0 -- course;
 
code -- course;
 
course -- "C-I" [label="n",len=1.00];
 
"C-I" -- institute [label="1",len=1.00];
 
  institute -- name1;
 
institute -- "S-I" [label="1",len=1.00];
 
"S-I" -- student [label="n",len=1.00];
 
student -- grade;
 
student -- name2;
 
student -- number;
 
student -- "S-C" [label="m",len=1.00];
 
"S-C" -- course [label="n",len=1.00];
 
label = "\n\nEntity Relation Diagram\ndrawn by CIRCO";
 
}
 
</circo>
 
 
 
= Версии для печати =
 
Как известно, трудно добиться хорошего результата одновременно на экране и на принтере, в силу разных разрешений. Картинка экранного разрешения будет плохо (с «зазубринами») выглядеть на принтере, а картинка печатного разрешения, будет очень плохо выглядеть на экране (к сожалению, современные броузеры выполняют очень примитивный ресайзинг картинок при показе), и будет достаточно много «весить». Все соображения о печатных картинках также относятся к случаю, когда вы переносите (например, копируя вебстраницу из броузера через клипборд) содержимое MediaWiki-статьи в MS Word или другой текстовый редактор.
 
Для такого, «печатного» случая (т. е. если у вас не примитивные графы, и вы собираетесь их печатать или переносить в другую систему верстки), мы сделали «печатную версию» всех перечисленных графов, с разрешением около 200 DPI. Для этого надо использовать те же самые тэги с постфиксом «-print», например «graph-print»,«neato-print», и т.п.:
 
 
 
<graph-print>
 
digraph G{
 
  rankdir=LR;
 
  node[color="red",fontsize=14];
 
  edge[color="darkgreen",fontcolor="blue",fontsize=12];
 
  OPEN[shape="rectangle",style="filled",fillcolor="lightgrey"];
 
  CLOSED[shape="octagon",label="Финиш"];
 
  VERIFIED[shape="rectangle",style="rounded"];
 
  OPEN->RESOLVED->VERIFIED->CLOSED;
 
  OPEN->CLOSED[style="bold"];
 
  VERIFIED->OPEN[label="обнаружены ошибки",style="dashed",arrowhead="dot"];
 
  }
 
</graph-print>
 
 
 
Полученные картинки являются компромиссом, между весом, читаемостью на экране и читаемостью на бумаге.
 
Желательно не использовать для совершенно тривиальных графов, или графов, которых вы не собираетесь печатать.
 
 
 
 
 
 
 
  
 +
== [http://lib.custis.ru/index.php/Graphviz Побробнее о Graphviz] ==
  
[[Категория:Семинар]]
+
[[Категория:Веб 2.0]]

Текущая версия на 10:00, 19 февраля 2015

Graphviz - набор утилит для графического представления данных. Программа принимает описания отношений и элементов множеств, на которых определяется граф, и "добавляет" к этим лишенным всяких геометрических атрибутов описаниям дополнительную информацию, позволяющую "нарисовать" картинку графа.

Для использования Графвиз требуется использовать примитивный язык описания графов dgl. Основные понятия:

  • граф,
  • вершина графа -- элемент множества,
  • ребро графа, соединяющее вершину N с вершиной M

Быстрый старт

Входной файл для программы «DOT» является обычным текстовым файлом на специальном языке разметки графа. Структура файла очень простая, например,

 <graphviz> 
 digraph G{
 Рождение->Юность->Зрелость->Старость->Смерть;
 Юность->Смерть;
 Зрелость->Смерть;
 }
 </graphviz>

на выходе будет:

<graphviz> digraph G{ Рождение->Юность->Зрелость->Старость->Смерть; Юность->Смерть; Зрелость->Смерть; } </graphviz>

Программа «Dot» сама распознает все связи графа и упорядочит его таким образом, чтобы было наименьшее количество пересечений.

Если у вас узлы поименованы словосочетаниями, заключите их в кавычки, например:

 <graphviz>
 digraph G{
 "Сидоров Пётр Фёдорович" -> "Сидоров Иван Петрович" [label="отец"];
 "Сидорова Анна Павловна " -> "Сидоров Иван Петрович" [label="мать"];
 } 
 </graphviz>

<graphviz>

digraph G{
"Сидоров Пётр Фёдорович" -> "Сидоров Иван Петрович" [label="отец"];
"Сидорова Анна Павловна " -> "Сидоров Иван Петрович" [label="мать"];
} 
</graphviz>

Свойства графа

Для того, граф было удобнее просматривать, можно настроить следующие свойства. Например:

  • Направленность графа:
    • rankdir=LR - слева-направо
    • rankdir=TB - сверху вниз
    • ratio=auto - отношение = авто;
  • Цвет фона графа - graph [bgcolor=Snow2] - окрашивает фон в цвет - "серый снег"
  • Свойства (node) узлов - node[color="Pink",fontsize=10, style=filled, fontcolor="blue", shape="none"] (Сочетание двух и более слов записывается в кавычки - "Нижний Новгород")
    • color="Pink" - цвет = розовый (Цвета в Вики)
    • fontsize=8 - размер шрифта = 8
    • style=filled - стиль = заполненный (без неё узел прозрачен)
    • fontcolor="blue" - цвет шрифта = голубой
    • shape="none" - форма = "без формы"
      • Формы узла [shape=?] - invtriangle - треугольник вершиной вниз; box - прямоугольник; ellipse - эллипс; invtrapezium - перевёрнутая трапеция; triangle - треугольник; trapezium - трапеция; octagon - восьмиугольник; tripleoctagon - тройной восьмиугольник (Все формы)
    • Ярославль [shape=Mdiamond] - узлу Ярославль придаётся форма ромба(алмаз)
    • Сызрань [shape=Msquare] - узлу Сызрань придаётся форма квадрата
    • Кострома [shape=circle] - узлу Кострома придаётся форма круга
    • "Нижний Новгород" [shape=doublecircle] - узлу "Нижний Новгород" придаётся форма двойного круга
    • Казань [shape=hexagon,color=green] - узлу Казань придаётся форма шестиугольника и зелёный цвет
  • Управление положением узлов - {rank=same; Елабуга Дзержинск Сызрань ;} - узлам Елабуга, Дзержинск, Сызрань предан разряд = тот же самый; ranksep=3 - расстояние между разрядами;
  • Свойства (edge) ребер - edge[color="blue",fontcolor="Green",fontsize=12]
    • color="Brown" - цвет = коричневый
      • color="Green:blue:red" - трёхцветие (возможно любое количество)
    • dir=both - направление стрелки в две стороны
    • fontsize=8 - размер шрифта = 8
    • fontcolor="blue" - цвет шрифта = зелёный
    • style=dotted - стиль = пунктирная линия
    • arrowhead="dot" - голова стрелки = "точка", "none" - нет (Все формы)
  • Ярлык ребра [label="Волга"] - все связи Ярославль -> ... -> Сызрань будут помечены меткой Волга.


Пример:

<graphviz>
 digraph G{
 graph [bgcolor=Snow2];
 rankdir=LR ; // направление графа слева направо
 node[color="Pink",fontsize=8, fontcolor="blue",style=filled, shape="none"] ;
 edge[color="Brown",fontcolor="Green",fontsize=8] ;
 Ярославль -> Кострома -> "Нижний Новгород" -> Казань -> Сызрань [dir=both, label="Волга"];
 "Нижний Новгород" -> Дзержинск [style=dotted, label="Ока",arrowhead="dot" ] ;
 Казань -> Елабуга [label="Кама", color="Green:blue:red"] ;
 Ярославль [shape=Mdiamond], Сызрань [shape=Msquare], Кострома [shape=circle];
 "Нижний Новгород" [shape = doublecircle],Казань[shape=hexagon,color=green]
 {rank=same; Елабуга Дзержинск Сызрань ;}
 }
 </graphviz>

Результат:

<graphviz>

digraph G{
graph [bgcolor=Snow2];
rankdir=LR ; 
node[color="Pink",fontsize=8, fontcolor="blue",style=filled, shape="none"] ;
edge[color="Brown",fontcolor="Green",fontsize=8] ;
Ярославль -> Кострома -> "Нижний Новгород" -> Казань -> Сызрань [dir=both, label="Волга"];
"Нижний Новгород" -> Дзержинск [style=dotted, label="Ока",arrowhead="dot" ] ;
Казань -> Елабуга [label="Кама", color="Green:blue:red"] ;
Ярославль [shape=Mdiamond], Сызрань [shape=Msquare], Кострома [shape=circle];
"Нижний Новгород" [shape = doublecircle],Казань[shape=hexagon,color=green]
{rank=same; Елабуга Дзержинск Сызрань ;}

}

</graphviz>

Побробнее о Graphviz