![有没有办法在物理包中定义 \xmat*{M}{n}{m}](https://linux22.com/image/394502/%E6%9C%89%E6%B2%A1%E6%9C%89%E5%8A%9E%E6%B3%95%E5%9C%A8%E7%89%A9%E7%90%86%E5%8C%85%E4%B8%AD%E5%AE%9A%E4%B9%89%20%5Cxmat*%7BM%7D%7Bn%7D%7Bm%7D.png)
正如标题,我希望命令\mqty(\xmat*{M}{n}{m})
生成这样的矩阵:
$$
\begin{pmatrix}
M_{ 11 } & M_{ 12 } & M_{ 13 } & \cdots & M_{ 1m } \\
M_{ 21 } & M_{ 22 } & M_{ 23 } & \cdots & M_{ 2m } \\
M_{ 31 } & M_{ 32 } & M_{ 33 } & \cdots & M_{ 3m } \\
\vdots & \vdots & \vdots & \ddots & \vdots \\
M_{ n1 } & M_{ n2 } & M_{ n3 } & \cdots & M_{ nm } \\
\end{pmatrix}
$$
另外,我希望这个命令也适用于有限列或行向量(如果这也可以用于无限阶的矩阵/向量就更好了)。(例如\xmat*{v}{n}{1}
)\xmat*{M}{5}{n}
我是否必须为每个文档创建一个新命令,或者是否有其他方法可以实现这一点?
谢谢
答案1
以下是使用 的实现expl3
。
的论点\xmat
是
*
(表示无限矩阵)- 矩阵分隔符的类型(可选,默认
p
) - 参赛信件
- 行数(可以是符号或显式整数)
- 明确显示的行数(可选,默认为 3)
- 列数(可以是符号或显式整数)
- 明确显示的列数(可选,默认为 3)
\documentclass{article}
\usepackage{amsmath}
\usepackage{xparse}
\ExplSyntaxOn
% #1 = star
% #2 = letter for the matrix delimiters (p,b,B,v,V), default = p
% #3 = letter for the entries
% #4 = number of rows
% #5 = number of explicit rows, default = 3
% #6 = number of columns
% #7 = number of explicit columns, default = 3
\NewDocumentCommand{\xmat}{sO{p}mmO{3}mO{3}}
{
\IfBooleanTF { #1 }
{% with \xmat* we want an infinite matrix
\bool_set_true:N \l__wang_xmat_infinite_bool
}
{
\bool_set_false:N \l__wang_xmat_infinite_bool
}
\wang_xmat:nnnnnn { #2 } { #3 } { #4 } { #5 } { #6 } { #7 }
% t l r mr c mc
}
\bool_new:N \l__wang_xmat_infinite_bool
\bool_new:N \l__wang_xmat_dotrow_bool
\bool_new:N \l__wang_xmat_dotcol_bool
\tl_new:N \l__wang_xmat_body_tl
\int_new:N \l__wang_xmat_exrows_int
\int_new:N \l__wang_xmat_excols_int
\cs_new_protected:Nn \wang_xmat:nnnnnn
{
% clear the variable containing the body of the matrix
\tl_clear:N \l__wang_xmat_body_tl
% set the tentative number of explicit rows
\int_set:Nn \l__wang_xmat_exrows_int { #4 }
\regex_match:nnTF { \A [[:digit:]]* \Z } { #3 }
{% number of rows is an integer
\int_compare:nTF { #3 <= #4 }
{% if #3 <= #4 we don't want a row of dots
\bool_set_false:N \l__wang_xmat_dotrow_bool
\int_set:Nn \l__wang_xmat_exrows_int { #3 }
}
{% we want a row of dots
\bool_set_true:N \l__wang_xmat_dotrow_bool
}
}
{% number of rows is symbolic, we want a row of dots
\bool_set_true:N \l__wang_xmat_dotrow_bool
}
% set the tentative number of explicit columns
\int_set:Nn \l__wang_xmat_excols_int { #6 }
\regex_match:nnTF { \A [[:digit:]]* \Z } { #5 }
{% number of cols is an integer
\int_compare:nTF { #5 <= #6 }
{% if #5 <= #6 we don't want a column of dots
\bool_set_false:N \l__wang_xmat_dotcol_bool
\int_set:Nn \l__wang_xmat_excols_int { #5 }
}
{% we want a column of dots
\bool_set_true:N \l__wang_xmat_dotcol_bool
}
}
{% number of columns is symbolic, we want a column of dots
\bool_set_true:N \l__wang_xmat_dotcol_bool
}
% loop through the rows
\int_step_inline:nn { \l__wang_xmat_exrows_int }
{
% add the first entry in the row
\tl_put_right:Nn \l__wang_xmat_body_tl { #2\sb{##1 1} }
% add the further entries in the explicit columns
\int_step_inline:nnn { 2 } { \l__wang_xmat_excols_int }
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & #2\sb{##1 ####1} }
}
% if we have a column of dots, add \cdots and the last entry
\bool_if:NT \l__wang_xmat_dotcol_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \cdots & #2\sb{##1 #5} }
}
% infinite matrix, add \cdots
\bool_if:NT \l__wang_xmat_infinite_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \cdots }
}
% finish up the row
\tl_put_right:Nn \l__wang_xmat_body_tl { \\ }
}
% finish up the rows
\bool_if:NT \l__wang_xmat_dotrow_bool
{
% if we have a row of dots, fill it in
\tl_put_right:Nn \l__wang_xmat_body_tl { \vdots }
\prg_replicate:nn { \l__wang_xmat_excols_int - 1 }
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \vdots }
}
\bool_if:NT \l__wang_xmat_dotcol_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \ddots & \vdots }
}
\tl_put_right:Nn \l__wang_xmat_body_tl { \\ }
% fill the last row
\tl_put_right:Nn \l__wang_xmat_body_tl { #2\sb{#3 1} }
\int_step_inline:nnn { 2 } { \l__wang_xmat_excols_int }
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & #2\sb{#3 ##1} }
}
\bool_if:NT \l__wang_xmat_dotcol_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \cdots & #2\sb{#3 #5} }
}
% if the matrix is infinite, add a further column with \cdots
\bool_if:NT \l__wang_xmat_infinite_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \cdots }
}
% finish up the row
\tl_put_right:Nn \l__wang_xmat_body_tl { \\ }
}
% if the matrix is infinite, add a final row
\bool_if:NT \l__wang_xmat_infinite_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { \vdots }
\prg_replicate:nn { \l__wang_xmat_excols_int - 1 }
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & \vdots }
}
\bool_if:NT \l__wang_xmat_dotcol_bool
{
\tl_put_right:Nn \l__wang_xmat_body_tl { & & \vdots }
}
\tl_put_right:Nn \l__wang_xmat_body_tl { & \ddots }
}
% typeset the matrix
\begin{#1matrix}\l__wang_xmat_body_tl\end{#1matrix}
}
\ExplSyntaxOff
\begin{document}
\[
\xmat{M}{m}{n} \xmat*[b]{M}{m}{n}
\]
\[
\xmat{M}{m}[2]{n}[4] \xmat*[b]{M}{m}[4]{n}[2]
\]
\[
\xmat{v}{1}{n} \xmat{v}{m}{1} \xmat{v}{m}{2} \xmat{a}{2}{2} \xmat*[v]{a}{2}{2}
\]
\[
\xmat[]{M}{m}{n}
\]
\end{document}
如果您想要一个无限制矩阵,请调用\xmat[]{M}{m}{n}
。
我认为没有办法仅使用physics
包中的工具来实现这一点(我觉得使用起来很奇怪也很尴尬,所以我从不推荐它)。