在 Matlab 中,我可以通过键入 来创建一个矩阵A = [1 2 3; 4 5 6; 7 8 9]
,其中空格是矩阵条目之间的分隔符。我想知道是否有一个包可以以类似的方式直接将数值数组输入到 LaTeX 中?
例如,我想要使用以下语法:
$\SpaceDelimMat[c]{1 2 3; 4 5 6; 7 8 9}$,
而不需要像这样输入 6 次 & (& 符号):
$\left[\begin{array}[c]{rrr} 1 & 2 & 3\\ 4 & 5 & 6\\ 7 & 8 & 9\end{array}\right]$;
因为后者非常耗时,并且会使 LaTeX 文档的可读性降低,尤其是在介绍矩阵课程时。
答案1
使用 LaTeX3 宏非常容易。
\documentclass{article}
\usepackage{xparse,amsmath}
\ExplSyntaxOn
\NewDocumentCommand{\matlabmatrix}{ O{b} m }
{
\strategy_matlabmatrix:nn { #1 } { #2 }
}
\seq_new:N \l_strategy_rows_seq
\seq_new:N \l_strategy_a_row_seq
\tl_new:N \l_strategy_matrix_tl
\cs_new_protected:Npn \strategy_matlabmatrix:nn #1 #2
{
\tl_clear:N \l_strategy_matrix_tl
\seq_set_split:Nnn \l_strategy_rows_seq { ; } { #2 }
\seq_map_inline:Nn \l_strategy_rows_seq
{
\seq_set_split:Nnn \l_strategy_a_row_seq { ~ } { ##1 }
\tl_put_right:Nx \l_strategy_matrix_tl { \seq_use:Nn \l_strategy_a_row_seq { & } }
\tl_put_right:Nn \l_strategy_matrix_tl { \\ }
}
\begin{#1matrix}
\tl_use:N \l_strategy_matrix_tl
\end{#1matrix}
}
\ExplSyntaxOff
\begin{document}
\[
\matlabmatrix{1 2 3; 4 5 6; 7 8 9}
\ne
\matlabmatrix[p]{1 2 3; 4 5 6; 7 8 9}
\]
\end{document}
我们首先在分号处拆分参数,然后通过在空格处拆分来处理每个项目。包含矩阵主体的标记列表变量逐行填充,然后在适当的环境中传递amsmath
。可选参数(默认b
,括号)可以是p
(圆括号)、v
(单杠)、V
(双杠)、B
(大括号)甚至是空的(无分隔符)。
可定制版本
还可以定义一个非常可定制的\xmatlabmatrix
,以可选参数键值选项为准;选项包括
alignment = t | c | b % vertical alignment
columns = <column specifiers> % default all centered
delimiters = brackets | parens | braces | bars | doublebars | empty % fences
colsep = <character>
rowsep = <character>
默认的 forcolsep
是空格,但可以使用键在本地自定义,也可以\matlabmatrixsetup
在前言中全局自定义。在示例中,它位于正文中;实际上,它可以在任何地方发出,并遵守作用域规则(请记住,colsep={,}
for 为逗号,colsep={ }
for 为空格,并使用括号)。
以下是代码
\documentclass{article}
\usepackage{xparse,amsmath,delarray}
\ExplSyntaxOn
\NewDocumentCommand{\matlabmatrix}{ O{b} m }
{
\strategy_matlabmatrix:nn { #1 } { #2 }
}
\NewDocumentCommand{\matlabmatrixsetup}{m}
{
\keys_set:nn { strategy/matrix } { #1 }
}
\seq_new:N \l_strategy_rows_seq
\seq_new:N \l_strategy_a_row_seq
\tl_new:N \l_strategy_matrix_tl
\cs_new_protected:Npn \strategy_matlabmatrix:nn #1 #2
{
\strategy_build_matrix:n { #2 }
\begin{#1matrix}
\tl_use:N \l_strategy_matrix_tl
\end{#1matrix}
}
\cs_new_protected:Npn \strategy_build_matrix:n #1
{
\tl_clear:N \l_strategy_matrix_tl
\seq_set_split:NVn \l_strategy_rows_seq \l_strategy_rowsep_tl { #1 }
\seq_map_inline:Nn \l_strategy_rows_seq
{
\seq_set_split:NVn \l_strategy_a_row_seq \l_strategy_colsep_tl { ##1 }
\tl_put_right:Nx \l_strategy_matrix_tl { \seq_use:Nn \l_strategy_a_row_seq { & } }
\tl_put_right:Nn \l_strategy_matrix_tl { \\ }
}
}
\cs_generate_variant:Nn \seq_set_split:Nnn { NV }
\NewDocumentCommand{\xmatlabmatrix}{ O{} m }
{
\group_begin:
\keys_set:nn { strategy/matrix } { #1 }
\strategy_xmatlabmatrix:n { #2 }
\group_end:
}
\keys_define:nn { strategy/matrix }
{
alignment .tl_set:N = \l_strategy_matrix_alignment_tl,
alignment .initial:n = c,
columns .tl_set:N = \l_strategy_matrix_columns_tl,
columns .initial:n = *{100}{c},
delimiters .choice:,
delimiters / brackets .code:n =
\tl_set:Nn \l_strategy_ldel_tl { \lbrack }
\tl_set:Nn \l_strategy_rdel_tl { \rbrack },
delimiters / parens .code:n =
\tl_set:Nn \l_strategy_ldel_tl { ( }
\tl_set:Nn \l_strategy_rdel_tl { ) },
delimiters / braces .code:n =
\tl_set:Nn \l_strategy_ldel_tl { \lbrace }
\tl_set:Nn \l_strategy_rdel_tl { \rbrace },
delimiters / bars .code:n =
\tl_set:Nn \l_strategy_ldel_tl { \lvert }
\tl_set:Nn \l_strategy_rdel_tl { \rvert },
delimiters / doublebars .code:n =
\tl_set:Nn \l_strategy_ldel_tl { \lVert }
\tl_set:Nn \l_strategy_rdel_tl { \rVert },
delimiters / empty .code:n =
\tl_set:Nn \l_strategy_ldel_tl { }
\tl_set:Nn \l_strategy_rdel_tl { },
rowsep .tl_set:N = \l_strategy_rowsep_tl,
rowsep .initial:n = ;,
colsep .tl_set:N = \l_strategy_colsep_tl,
colsep .initial:n = {~},
}
\tl_new:N \l_strategy_ldel_tl
\tl_new:N \l_strategy_rdel_tl
\tl_set:Nn \l_strategy_ldel_tl { \lbrack }
\tl_set:Nn \l_strategy_rdel_tl { \rbrack }
\cs_new_protected:Npn \strategy_xmatlabmatrix:n #1
{
\strategy_build_matrix:n { #1 }
\use:x
{
\exp_not:N \begin {array}
[ \l_strategy_matrix_alignment_tl ]
\exp_not:V \l_strategy_ldel_tl
{ @{} \exp_not:V \l_strategy_matrix_columns_tl @{} }
\exp_not:V \l_strategy_rdel_tl
\exp_not:V \l_strategy_matrix_tl
\exp_not:N \end{array}
}
}
\ExplSyntaxOff
\begin{document}
\[
\matlabmatrix{1 2 3; 4 5 6; 7 8 9}
\ne
\matlabmatrix[p]{1 2 3; 4 5 6; 7 8 9}
\]
\[
\xmatlabmatrix[columns=ccc]{1 2 3; 4 5 6; 7 8 9}
+
\xmatlabmatrix[
alignment=t,
delimiters=parens,
columns=lcr
]{100 100 100; 2 2 2; -3 -3 -3}
\]
\matlabmatrixsetup{
colsep={,}
}
\[
\matlabmatrix{1,2,3; 4,5,6; 7,8,9}
\ne
\matlabmatrix[p]{1,2,3;4,5,6;7,8,9}
\]
\end{document}