15

是否有与 SQL Server 一起使用以从分层数据模型生成树状图的工具?

我正在处理一个大的地理层次结构,并希望将其可视化。

这是一个例子。

我有一个 NodeHierarchy 表,它存储节点之间的层次关系。表中的每一行代表一个节点。除了一个节点之外,每个节点都有一个父节点。如果层次结构,则没有父节点的节点是根节点。

这是我创建表的方式:

CREATE DATABASE HierarchyTest;
GO

USE HierarchyTest;
GO

CREATE TABLE NodeHierarchy (
  PK_NodeID INT NOT NULL
    CONSTRAINT PK_NodeHierarchy PRIMARY KEY,
  FK_ParentNodeID INT NULL
    CONSTRAINT FK_NodeHierarchy_NodeHierarchy FOREIGN KEY
      REFERENCES NodeHierarchy(PK_NodeID),
  Name NVARCHAR(255) NOT NULL
);

我有一个苏格兰城市和场地的示例层次结构。苏格兰是等级制度的根源。苏格兰的后裔是城市和场所。在这个层次结构中,父母“包含”一个孩子,所以我们说,例如“巴罗兰兹在格拉斯哥,格拉斯哥在苏格兰”。

此语句使用示例数据填充 NodeHierachy 表:

INSERT INTO NodeHierarchy(PK_NodeID, FK_ParentNodeID, Name)
VALUES
  (1, NULL, N'Scotland'),
  (2, 1, N'Glasgow'),
  (3, 1, N'Edinburgh'),
  (4, 1, N'St Andrews'),
  (5, 2, N'The Barrowlands'),
  (6, 2, N'The Cathouse'),
  (7, 2, N'Carling Academy'),
  (8, 2, N'SECC'),
  (9, 2, N'King Tut''s Wah-Wah Hut'),
  (10, 3, N'Henry''s Cellar Bar'),
  (11, 3, N'The Bongo Club'),
  (12, 3, N'Sneaky Pete''s'),
  (13, 3, N'The Picture House'),
  (14, 3, N'Potterrow'),
  (15, 4, N'Aikman''s'),
  (16, 4, N'The Union'),
  (17, 4, N'Castle Sands');

输出SELECT * FROM NodeHierarchy;

PK_NodeID   FK_ParentNodeID Name
----------- --------------- ---------------------------------
1           NULL            Scotland
2           1               Glasgow
3           1               Edinburgh
4           1               St Andrews
5           2               The Barrowlands
6           2               The Cathouse
7           2               Carling Academy
8           2               SECC
9           2               King Tut's Wah-Wah Hut
10          3               Henry's Cellar Bar
11          3               The Bongo Club
12          3               Sneaky Pete's
13          3               The Picture House
14          3               Potterrow
15          4               Aikman's
16          4               The Union
17          4               Castle Sands

(17 row(s) affected)

Freemind中,我画了这个等价图: 苏格兰场馆的思维导图

什么工具可以用最少的手动操作为我做到这一点?


编辑:最初我说我想可视化层次结构的“全部或部分”。此处发布的解决方案无条件地可视化整个层次结构。这对于较小的示例层次结构很好,但对于较大的示例层次结构,仅可视化其中的一部分可能更有用。

因为我没有具体说明“部分”的含义,所以我已将其从问题中删除。我在另一个问题中询问了部分可视化。

4

2 回答 2

10

我研究了 Cade Roux 回答中的线索,并使用 GraphViz 开发了一个解决方案。

要了解 GraphViz,首先我阅读了这篇介绍性文章命令行调用文档。从文章中的示例代码清单成功生成图表后,我对使用自己的数据充满信心。

正如 Cade 所建议的,学习 GraphViz 的 DOT 语言的最好方法是自己写出来。我研究了这篇文章的示例(清单 1、2 和 6),然后想出这个venues.gv来描述我自己的数据:

digraph Venues
{ 
  N1[label = "Scotland"];
  N2[label = "Glasgow"];
  N3[label = "Edinburgh"];
  N4[label = "St Andrews"];
  N5[label = "The Barrowlands"];
  N6[label = "The Cathouse"];
  N7[label = "Carling Academy"];
  N8[label = "SECC"];
  N9[label = "King Tut's Wah-Wah Hut"];
  N10[label = "Henry's Cellar Bar"];
  N11[label = "The Bongo Club"];
  N12[label = "Sneaky Pete's"];
  N13[label = "The Picture House"];
  N14[label = "Potterrow"];
  N15[label = "Aikman's"];
  N16[label = "The Union"];
  N17[label = "Castle Sands"];

  N1 -> N2;
  N1 -> N3;
  N1 -> N4;
  N2 -> N5;
  N2 -> N6;
  N2 -> N7;
  N2 -> N8;
  N2 -> N9;
  N3 -> N10;
  N3 -> N11;
  N3 -> N12;
  N3 -> N13;
  N3 -> N14;
  N4 -> N15;
  N4 -> N16;
  N4 -> N17;
}

我将它提供给circoGraphViz 的众多绘图命令之一,并得到了令人满意的输出:

输出circo -Tpng venues.gv -o venues.png

分层场地数据的可视化

GraphViz 文件由两个块构成。一个块为每个节点声明一个标签,另一个块声明图的边。

为了为这些块中的每一个提供数据,我创建了一个NodeHierarchy.

此视图提供数据来声明节点的标签:

CREATE VIEW NodeLabels (
  Node,
  Label
)
AS
SELECT
   PK_NodeID AS Node,
   Name AS Label
FROM
  NodeHierarchy;

此视图提供数据来声明节点之间的边:

CREATE VIEW Edges (
  Parent,
  Child
)
AS
SELECT
  FK_ParentNodeID AS Parent,
  PK_NodeID AS Child
FROM NodeHierarchy
WHERE FK_ParentNodeID IS NOT NULL;

这个称为 Powershell 脚本的脚本generate-graph.ps1从视图中选择数据,将其转换为 GraphViz 输入,然后通过管道将circo其生成完整层次结构的可视化,如上图所示:

"digraph Venues {" + (
  Invoke-Sqlcmd -Query "SELECT * FROM HierarchyTest.dbo.NodeLabels" | 
  ForEach-Object {"N" + $_.Node + "[label = """ + $_.Label + """];"}
) + (
  Invoke-Sqlcmd -Query "SELECT * FROM HierarchyTest.dbo.Edges" |
  ForEach-Object {"N" + $_.Parent + " -> N" + $_.Child + ";"}
) +
"}" | circo -Tpng -o venues.png

必须运行该脚本,sqlps而不是powershell这样Invoke-Sqlcmdcmdlet 才可用。的默认工作目录sqlpsSQLSERVER,所以我在运行脚本时必须指定驱动器sqlps

这是我用来生成类似上述图表的命令:

sqlps C:.\generate-graph.ps1

这将输出一个venues.png在 C 工作目录中调用的文件。

这个 Powershell 解决方案感觉有点不雅,但这正是我需要它做的。更有经验的 Powershell 程序员可能会想出一些更干净的东西。

于 2011-08-22T16:46:20.780 回答
8

Export and run it through GraphViz - you don't even have to generate the hierarchy (just export nodes and edges) - just assign node names which are unique based on your NodeID column and use those same node names in the edges.

If you want something interactive, Microsoft has a Automatic Graph Layout library which can be used from .NET.

Here's an introduction to GraphViz.

What you are going to do is output a DOT file by exporting your SQL using a script like this: https://data.stackexchange.com/stackoverflow/q/109885/ which will run through GraphViz and generate your picture.

The DOT syntax is relatively simple - you can write it by hand first and then generate that from SQL and simply paste it in a file or something else (like .NET or PowerShell) which reads the SQL sets and generates the file.

You can automate that with SSIS. I made a package which wrote out the DOT file and ran graphviz on it and saved a graphiacl snapshot of our system on a daily basis.

于 2011-08-18T17:35:59.583 回答