用于创建控制数字线条的宏

用于创建控制数字线条的宏

我想创建一个宏来实现以下效果:

假设这个命令名为command。然后我希望下面的命令提供我之后放置的图像。

\command{}
\command{}{$40$}{}
\command{$20$}{$10$}{$5$}{}{$3$}
\command{$100$}{$80$}{$50$}

在此处输入图片描述

有没有办法发出这样的命令?

答案1

最好有一个由逗号分隔的列表组成的参数。

\documentclass{article}
\usepackage{xparse}

\ExplSyntaxOn

\NewDocumentCommand{\overnumbers}{O{3}m}
 {% #1 = number of digits (optional), #2 = list of numbers
  \italo_overnumbers:nn { #1 } { #2 }
 }

\int_new:N \l__italo_overnumbers_digits_int
\seq_new:N \l__italo_overnumbers_list_seq
\tl_new:N \l__italo_overnumbers_first_tl

\cs_new_protected:Nn \italo_overnumbers:nn
 {
  \int_set:Nn \l__italo_overnumbers_digits_int { #1 }
  \__italo_overnumbers_prepare:n { #2 }
  \int_incr:N \l__italo_overnumbers_digits_int
  \__italo_overnumbers_print:
 }

\cs_new_protected:Nn \__italo_overnumbers_prepare:n
 {
  \seq_set_split:Nnn \l__italo_overnumbers_list_seq { , } { #1 }
  \seq_map_inline:Nn \l__italo_overnumbers_list_seq
   {
    \int_set:Nn \l__italo_overnumbers_digits_int
     {
      \int_max:nn { \l__italo_overnumbers_digits_int } { \tl_count:n { ##1 } }
     }
   }
 }

\cs_new_protected:Nn \__italo_overnumbers_print:
 {
  \seq_pop_left:NN \l__italo_overnumbers_list_seq \l__italo_overnumbers_first_tl  
  \__italo_overnumbers_make:V \l__italo_overnumbers_first_tl
  \seq_map_inline:Nn \l__italo_overnumbers_list_seq
   {
    \hspace*{0.5em}
    \__italo_overnumbers_make:n { ##1 }
   }
 }
\cs_new_protected:Nn \__italo_overnumbers_make:n
 {
  \ensuremath{\overline{
    \makebox[\dim_eval:n { (0.5em)*\l__italo_overnumbers_digits_int}]
     {
      $#1\vphantom{0}$
     }
  }}
 }
\cs_generate_variant:Nn \__italo_overnumbers_make:n { V }

\ExplSyntaxOff

\begin{document}

\overnumbers{}

\medskip

\overnumbers{,40,}

\medskip

\overnumbers{20,10,5,,3}

\medskip

\overnumbers{100,80,50}

\medskip

\overnumbers[4]{100,80,50}

\medskip

\overnumbers[2]{80,,50}

\medskip

\overnumbers{20080,50}

\end{document}

可选参数(默认为 3)表示数字的数量,但它会自动更新以适应更大的数字,请参阅最后一个例子。

在此处输入图片描述

答案2

我的意思是使用\command{a,b,c}Instead\command{$a$}{$b$}{$c$}更好。

\def\ruleabove{\vrule width15pt height.8pt}
\def\command#1{\hbox{\commandA#1,\end,\unskip}}
\def\commandA#1,{\ifx\end#1\relax \else 
   \vtop{\halign{\hfil##\hfil\cr\ruleabove\cr\noalign{\kern-2pt}$#1$\cr}}\quad
   \expandafter\commandA\fi}

\command{21, 10, 5, , 3}

\bye

答案3

如果您愿意考虑使用逗号分隔列表,这里有许多选项可以按照您的建议进行操作。(否则,锡拉库萨指出,事情可能会变得更加复杂。)

\documentclass{article}
\usepackage{amsmath}
\usepackage{pgffor}
\newcommand{\multioverline}[1]{\foreach \X[count=\Y] in {#1}
{\pgfmathsetmacro{\mywidth}{max(12pt,width("\X")+3pt)}
\ifnum\Y=1
\ensuremath{\overline{\mathstrut\makebox[\mywidth pt][c]{\X}}}%
\else
~\ensuremath{\overline{\mathstrut\makebox[\mywidth pt][c]{\X}}}%
\fi}}
\begin{document}
\multioverline{20,10,5,,3}
\end{document}

在此处输入图片描述

答案4

我猜想原作者希望上划线单位的宽度是固定的,而不是随着参数的增长而增长。因此,如果要容纳更大的数字,那么只需增加1.8em宏中的规则长度即可。

规则的厚度、长度和重叠间隙都是宏中指定的长度,可以根据需要进行更改。

\documentclass{article}
\usepackage{stackengine,listofitems}
\newcommand\moverline[1]{%
  \setsepchar{,}%
  \readlist*\mynums{ #1}%
  \foreachitem\x\in\mynums[]{%
    \stackengine{0pt}{\,\,\rule[.95\ht\strutbox]{1.8em}{.6pt}\,\,}{\x}{O}{c}{F}{T}{L}%
  }%
}
\parskip=1.5ex
\begin{document}
\moverline{}

\moverline{,40,}

\moverline{20,10,5,,3}

\moverline{100, 80,  50}

\moverline{100,20000,300} $<$--- perhaps adjust rule length
\end{document}

在此处输入图片描述

相关内容