
решение1
с nicematrix
, это очень просто
\documentclass{article}
\usepackage{nicematrix}
\begin{document}
\[
\mathbf{A}_H =
\begin{bNiceMatrix}[first-row,first-col]
& v_6 & v_3 & v_4 & v_5 & v_1 & v_2 \\
v_6 & 0 & 1 & 0 & 1 & 0 & 0 \\
v_3 & 1 & 0 & 1 & 0 & 0 & 1 \\
v_4 & 0 & 1 & 0 & 1 & 0 & 0 \\
v_5 & 1 & 0 & 1 & 0 & 1 & 0 \\
v_1 & 0 & 0 & 0 & 1 & 0 & 1 \\
v_2 & 0 & 1 & 0 & 0 & 1 & 0 \\
\end{bNiceMatrix}
\]
\end{document}
решение2
Это интересная проблема. Здесь я определяю структуру данных для графов, позволяющую печатать матрицу смежности, но мы можем представить себе и другие варианты использования.
Идея состоит в том, чтобы хранить индексы вершин в одной последовательности, а список ребер — в другой последовательности.
Список вершин отображается (дважды) для проверки того, находится ли заданное ребро в списке ребер; в этом случае 1
добавляется к телу матрицы, в противном случае 0
.
Использование nicematrix
позволяет также заполнить внешнюю строку и столбец.
\documentclass{article}
\usepackage{nicematrix}
\ExplSyntaxOn
\NewDocumentCommand{\definegraph}{mmm}
{% #1 = graph name, #2 = vertex list, #3 = edge list
\ryl_graph_define:nnn { #1 } { #2 } { #3 }
}
\NewDocumentCommand{\adjacencymatrix}{m}
{% #1 = graph name
\ryl_graph_adjacency:n { #1 }
}
\cs_new_protected:Nn \ryl_graph_define:nnn
{
\seq_clear_new:c { l__graph_vertex_#1_seq }
\seq_set_from_clist:cn { l__graph_vertex_#1_seq } { #2 }
\seq_clear_new:c { l__graph_edge_#1_seq }
\seq_set_from_clist:cn { l__graph_edge_#1_seq } { #3 }
}
\tl_new:N \l__ryl_graph_adjacency_tl
\cs_new_protected:Nn \ryl_graph_adjacency:n
{
\tl_clear:N \l__ryl_graph_adjacency_tl
\seq_map_inline:cn { l__graph_vertex_#1_seq }
{
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { & v\sb{##1} }
}
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { \\ }
\seq_map_inline:cn { l__graph_vertex_#1_seq }
{
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { v\sb{##1} }
\seq_map_inline:cn { l__graph_vertex_#1_seq }
{
\seq_if_in:cnTF { l__graph_edge_#1_seq } { ##1-####1 }
{% the edge is in
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { & 1 }
}
{
\seq_if_in:cnTF { l__graph_edge_#1_seq } { ####1-##1 }
{% the edge is in
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { & 1 }
}
{
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { & 0 }
}
}
}
\tl_put_right:Nn \l__ryl_graph_adjacency_tl { \\ }
}
\begin{bNiceMatrix}[first-row,first-col]
\tl_use:N \l__ryl_graph_adjacency_tl
\end{bNiceMatrix}
}
\ExplSyntaxOff
\definegraph{A}{1,2,3}{1-2,1-3,2-3}
\definegraph{B}{6,3,4,5,1,2}{6-3,6-5,3-6,3-4,3-2,4-3,4-5,5-1,1-2}
\begin{document}
\[
\adjacencymatrix{A}
\]
\[
\mathbf{A}_{H}=\adjacencymatrix{B}
\]
\end{document}
Во втором примере видно, что перечисление повторяющихся ребер не имеет значения.