有没有办法从GraphPlot生成的图形的(FullForm或InputForm)中提取GraphPlot应用于GraphPlot规则的顶点顺序?我不想使用GraphUtilities函数VertexList。我也知道GraphCoordinates,但这两个函数都可以处理图形,而不是GraphPlot的图形输出。
例如,
gr1 = {1 -> 2, 2 -> 3, 3 -> 4, 4 -> 5, 5 -> 6, 6 -> 1};
gp1 = GraphPlot[gr1, Method -> "CircularEmbedding",
VertexLabeling -> True];
Last@(gp1 /. Graphics[Annotation[x___], ___] :> {x})提供了以下六个坐标对的列表:
VertexCoordinateRules -> {{2.,0.866025},{1.5,1.73205},{0.5,1.73205},{0.,0.866025},{0.5,1.3469*10^-10},{1.5,0}}
我如何知道哪个规则适用于哪个顶点,以及我能否确定这与VertexListgr1给出的规则相同
例如
Needs["GraphUtilities`"];
gr2 = SparseArray@
Map[# -> 1 &, EdgeList[{2 -> 3, 3 -> 4, 4 -> 5, 5 -> 6}]];
VertexList[gr2]给出{1,2,3,4,5}
但是...
gp2 = GraphPlot[gr2, VertexLabeling -> True,
VertexCoordinateRules ->
Thread[VertexList[gr1] ->
Last@(gp1 /. Graphics[Annotation[x___], ___] :> {x})[[2]]]];
Last@(gp2 /. Graphics[Annotation[x___], ___] :> {x})给出了六个坐标集:
VertexCoordinateRules -> {{2.,0.866025},{1.5,1.73205},{0.5,1.73205},{0.,0.866025},{0.5,1.3469*10^-10},{1.5,0}}
例如,我如何为gr2的VertexCoordinateRules抽象正确的VertexList?
(我意识到我可以通过在生成gr2后获取VertexList来纠正一些事情,例如)
VertexList@
SparseArray[
Map[# -> 1 &, EdgeList[{2 -> 3, 3 -> 4, 4 -> 5, 5 -> 6}]], {6, 6}]{1,2,3,4,5,6}
但是我需要的信息似乎出现在GraphPlot图形中:我如何获得它?
(我将图转换为邻接矩阵的原因是,正如Wolfram的Carl Woll所指出的那样,它允许我包括一个“孤立”节点,就像在gp2中一样)

发布于 2020-10-04 15:56:48
p2 = Normal@gp1 // Cases[#, Line[points__] :> points, Infinity] &;
p3 = Flatten[p2, 1];
ListLinePlot[p3[[All, 1 ;; 2]]]

V12.0.0
发布于 2010-11-23 04:43:01
使用顶点标记,一种方法是获得标签的坐标。请注意,GraphPlot的输出是GraphicsComplex格式的,其中坐标别名的坐标是第一个标注,您可以将其获取为
points = Cases[gp1, GraphicsComplex[points_, __] :> points, Infinity] // First查看FullForm,您将看到标签位于文本对象中,将它们提取为
labels = Cases[gp1, Text[___], Infinity]实际的标签似乎有两层深,所以你可以得到
actualLabels = labels[[All, 1, 1]];坐标别名是第二个参数,因此可以按如下方式获取它们
coordAliases = labels[[All, 2]]实际坐标是在GraphicsComplex中指定的,因此我们以如下方式获取它们
actualCoords = points[[coordAliases]]坐标列表和标签列表之间存在一一对应关系,因此您可以使用Thread将它们作为"label"->coordinate对的列表返回。
这是一个函数,它将所有这些结合在一起
getLabelCoordinateMap[gp1_] :=
Module[{points, labels, actualLabels, coordAliases, actualCoords},
points =
Cases[gp1, GraphicsComplex[points_, __] :> points, Infinity] //
First;
labels = Cases[gp1, Text[___], Infinity];
actualLabels = labels[[All, 1, 1]];
coordAliases = labels[[All, 2]];
actualCoords = points[[coordAliases]];
Thread[actualLabels -> actualCoords]
];
getLabelCoordinateMap[gp1]这并不是说这只适用于标记的GraphPlot。对于没有标签的对象,您可以尝试从其他图形对象中提取,但根据提取贴图的对象的不同,可能会得到不同的结果,因为似乎存在一个错误,有时会将线端点和顶点标签分配给不同的顶点。我已经上报了。解决这个bug的方法是总是使用显式的顶点->坐标规范来表示VertexCoordinateList,或者总是使用“邻接矩阵”表示法。这里有一个不一致的例子
graphName = {"Grid", {3, 3}};
gp1 = GraphPlot[Rule @@@ GraphData[graphName, "EdgeIndices"],
VertexCoordinateRules -> GraphData[graphName, "VertexCoordinates"],
VertexLabeling -> True]
gp2 = GraphPlot[GraphData[graphName, "AdjacencyMatrix"],
VertexCoordinateRules -> GraphData[graphName, "VertexCoordinates"],
VertexLabeling -> True]顺便说一句,这里是我用来在邻接矩阵和边规则表示之间进行转换的实用函数
edges2mat[edges_] := Module[{a, nodes, mat, n},
(* custom flatten to allow edges be lists *)
nodes = Sequence @@@ edges // Union // Sort;
nodeMap = (# -> (Position[nodes, #] // Flatten // First)) & /@
nodes;
n = Length[nodes];
mat = (({#1, #2} -> 1) & @@@ (edges /. nodeMap)) //
SparseArray[#, {n, n}] &
];
mat2edges[mat_List] := Rule @@@ Position[mat, 1];
mat2edges[mat_SparseArray] :=
Rule @@@ (ArrayRules[mat][[All, 1]] // Most)发布于 2010-11-22 22:10:05
如果你执行FullForm[gp1],你会得到一堆我不会在这里发布的输出。在输出的开头附近,您会发现一个GraphicsComplex[]。本质上,这是一个点的列表,然后是这些点的使用列表。因此,对于图形gp1,GraphicsComplex的开头是:
GraphicsComplex[
List[List[2., 0.866025], List[1.5, 1.73205], List[0.5, 1.73205],
List[0., 0.866025], List[0.5, 1.3469*10^-10], List[1.5, 0.]],
List[List[RGBColor[0.5, 0., 0.],
Line[List[List[1, 2], List[2, 3], List[3, 4], List[4, 5],
List[5, 6], List[6, 1]]]],第一个最外面的列表定义了6个点的位置。第二个最外面的列表使用第一个列表中的点的编号定义了这些点之间的一串线。如果你把这个玩弄一下,可能更容易理解。
EDIT:响应OP的注释,如果我执行:
FullForm[GraphPlot[{3 -> 4, 4 -> 5, 5 -> 6, 6 -> 3}]]我得到了
Graphics[Annotation[GraphicsComplex[List[List[0.`,0.9997532360813222`],
List[0.9993931236462025`,1.0258160108662504`],List[1.0286626995939243`,
0.026431169015735057`],List[0.02872413637035287`,0.`]],List[List[RGBColor[0.5`,0.`,0.`],
Line[List[List[1,2],List[2,3],List[3,4],List[4,1]]]],List[RGBColor[0,0,0.7`],
Tooltip[Point[1],3],Tooltip[Point[2],4],Tooltip[Point[3],5],Tooltip[Point[4],6]]],
List[]],Rule[VertexCoordinateRules,List[List[0.`,0.9997532360813222`],
List[0.9993931236462025`,1.0258160108662504`],
List[1.0286626995939243`,0.026431169015735057`],List[0.02872413637035287`,0.`]]]],
Rule[FrameTicks,None],Rule[PlotRange,All],Rule[PlotRangePadding,Scaled[0.1`]],
Rule[AspectRatio,Automatic]]顶点位置列表是GraphicsComplex中的第一个列表。在稍后的FullForm中,您可以看到一个列表,其中Mathematica添加了工具提示,以便使用您在原始边列表中提供的标识符来标记顶点。由于您现在看到的是描述图形的代码,因此您的顶点和将要绘制的内容之间只存在间接关系;信息都在那里,但不是完全直接解包。
https://stackoverflow.com/questions/4245946
复制相似问题