![在 LuaTeX 中选择一个特定的数组元素?](https://linux22.com/image/357885/%E5%9C%A8%20LuaTeX%20%E4%B8%AD%E9%80%89%E6%8B%A9%E4%B8%80%E4%B8%AA%E7%89%B9%E5%AE%9A%E7%9A%84%E6%95%B0%E7%BB%84%E5%85%83%E7%B4%A0%EF%BC%9F.png)
我需要创建一个命令,执行\MyCommand{x,y}
或\MyCommand{x,y,z}
(两种方式都应该是可能的),其中x
,,y
和z
是三个数字。它应该分别给出输出\begin{matrix}x\\y\end{matrix}
和\begin{matrix}x\\y\\z\end{matrix}
。
并且该命令应该只有一个以逗号分隔的参数,如所示。
我不太熟悉在 LaTeX 中使用 Lua 代码。但我还是尝试了以下方法。
\newcommand*{\MyCommand}[1]{%
\directlua {
str={#1}
if str[3]==nil then
tex.sprint([[\begin{matrix}]] .. str[1] .. [[\\]] .. str[2] .. [[\\]] .. [[\end{matrix}]])
else
tex.sprint([[\begin{matrix}]] .. str[1] .. [[\\]] .. str[2] .. [[\\]] .. str[3] .. [[\end{matrix}]])
end
}
}%
请让我知道我哪里错了,或者我如何开发这个命令。
我正在使用 MikTeX 分布和 LuaLaTeX 输出模式。
这是 MWE
\documentclass{article}
\usepackage{amsmath}
\newcommand*{\MyCommand}[1]{%
\directlua {
str={#1}
if str[3]==nil then
tex.sprint([[\begin{matrix}]] .. str[1] .. [[\\]] .. str[2] .. [[\\]] .. [[\end{matrix}]])
else
tex.sprint([[\begin{matrix}]] .. str[1] .. [[\\]] .. str[2] .. [[\\]] .. str[3] .. [[\end{matrix}]])
end
}
}%
\begin{document}
$\MyCommand{x,y}$\\
$\MyCommand{x,y,z}$
\end{document}
答案1
我只会在 TeX 中执行此操作(请注意,你省略了amsmath
)
\documentclass{article}
\usepackage{amsmath}
\newcommand*{\MyCommand}[1]{\begin{matrix}\relax\zz#1,\end{matrix}}
\def\zz#1,#2{#1\ifx\end#2\else\expandafter\\\expandafter\zz\fi#2}
\begin{document}
$\MyCommand{x,y}$
$\MyCommand{x,y,z}$
\end{document}
对于 Lua 版本,您需要记住,宏在传递给 lua 之前会展开,因此您可以放置\unexpanded{....}
完整的参数,但您还需要将表的元素设置为 lua 字符串,'x'
而不是(如您所见)未定义的 lua 变量,x
因此如果这样做,您将需要额外的字符串引用层。或者更简单地将整个内容视为字符串,然后,
使用\\
Lua 替换进行替换
\documentclass{article}
\usepackage{amsmath}
\newcommand*{\MyCommand}[1]{%
\begin{matrix}%
\directlua{
s=string.gsub('\luaescapestring{#1}',',','\string\\\string\\')
tex.sprint(s)}%
\end{matrix}}
\begin{document}
$\MyCommand{x,y}$
$\MyCommand{x,y,z}$
\end{document}
答案2
另一个简单版本(但带有expl3
)。对于图像,我已将其替换matrix
为pmatrix
。它也是可扩展的(未指定逗号列表元素数)。
\documentclass{article}
\usepackage{amsmath}
\usepackage{expl3,xparse}
\ExplSyntaxOn
\NewDocumentCommand { \MyCommand } { m }
{
\begin{matrix}
\seq_set_from_clist:Nn \l_tmpa_seq { #1 }
\seq_use:Nn \l_tmpa_seq { \\ }
\end{matrix}
}
\ExplSyntaxOff
\begin{document}
$\MyCommand{x,y}$
$\MyCommand{x,y,z}$
$\MyCommand{x,y,z,a,b}$
\end{document}
答案3
以下答案与大卫的. 主要区别在于使用lua代码包,它提供了一个名为 的环境luacode
。在luacode
环境中,大多数 TeX 的“特殊”字符—— #
、$
、%
、^
、&
、{
、}
——~
都可以直接输入。(这对于%
字符特别有用,它在 Lua 的一些模式匹配和数学相关函数中具有自己的特殊含义。TeX 的“特殊”字符中唯一需要特殊处理的是反斜杠字符 :\
它必须输入为\\
。要输入双反斜杠,必须输入\\\\
。最后,Lua 风格的行注释可以在luacode
环境中使用。
另外需要注意的是:请注意宏的使用\luastringN
,该宏也是由luacode
包提供的,用于将 LaTeX 宏的参数传递给 Lua 函数。在我看来,它\luastringN{#1}
比 更容易记住(当然也更容易看...)'\luaescapestring{\unexpanded{#1}}'
。:-)
% !TeX program = lualatex
\documentclass{article}
\usepackage{luacode} % for 'luacode' env. and '\luastringN' macro
%% Lua-side code
\begin{luacode}
function comma2double_backslash ( s )
-- replace all commas with double-backslashes
tex.sprint ((s:gsub ( ',' , '\\\\' )))
end
\end{luacode}
%% TeX-side code
\newcommand*{\MyCommand}[1]{%
\begin{array}{@{}c@{}}
\directlua{comma2double_backslash ( \luastringN{#1} )}
\end{array}%
}
\begin{document}
$\MyCommand{x,y}$
$\MyCommand{x,y,z}$
\end{document}