在T E X中,如何将字符串拆分\mana{X1 2W/UB R /G}成部分并将它们提供给另一个宏(在这种情况下,通过类似的方式替换宏调用\m{X}\m{12}\m{W/U}\m{B}\m{R/G}),通过非常简单的规则进行分组,即:a)连续数字形成一个组,b)斜线创建一组两个附近的字符,c)空格是否被完全剥离?
我尝试了这个substr包,但它没有太大帮助,只允许找到某些子串.手写循环如
\def\lcpass#1.{}
\def\lcloop#1#2.{%
\ifempty{#2}%
#1%
\let\continue=\lcpass%
\else%
\let\continue=\lcloop%
\fi%
\continue#2.}
\def\lastchar#1{\lcloop#1.} % returns the last character of a string
Run Code Online (Sandbox Code Playgroud)
当字符串以空格结尾时无法工作,我也没有成功\futurelet.
一般来说,如何处理在T E X 中解析字符串的任务?例如,texmate包允许人们编写类似的内容|1 e4 e5 Nf3 Nc6|并自动绘制相应的国际象棋位置.它是如何做到的?关于字符串中的字符循环和其他类似的T E X黑客,我能读到什么?
\def\m#1{\par$m$({\tt #1})}% Any macros
\def\removespaces{\catcode`\ =9 }% Ignore all spaces`
\let\manaNext\relax % aux def
\let\manaLastChar\relax % aux def
\newtoks\manaToks % aux toks
\newif\ifDigitProcessing
\def\mana#{\afterassignment \manaA \let\next= }% always next = {
\def\manaA{\bgroup \removespaces \let\manaNext\manaB \manaNext}% algorithm init: ignore spaces
\def\manaB{\futurelet\next\manaC}% algorithm start
\def\manaC{\ifx\next\egroup \def\nnext{\manaFlush\aftergroup\manaNext}\else\let\nnext\manaD\fi\nnext}% check for \egroup
\def\manaD{\ifx\next/\let\nnext\manaSlash\else \ifcat\next 1\let\nnext\manaDigit \else \let\nnext\manaE \fi\fi \nnext}% cases
\def\manaE#1{\manaFlush\DigitProcessingfalse\let\manaLastChar\next\manaNext}% Letters A-Z and a-z case
\def\manaFlush{\ifx\manaLastChar\relax\else\m{\manaLastChar}\fi\let\manaLastChar\relax
\ifDigitProcessing\expandafter\m\expandafter{\the\manaToks}\fi\manaToks{}}% transform to \m{...}
\def\manaSlash#1#2{\m{\manaLastChar/#2}\let\manaLastChar\relax\manaNext}%#1=/, #2=next letter
\def\manaDigit#1{\ifDigitProcessing\else\manaFlush\fi
\manaToks=\expandafter{\the\manaToks#1}\DigitProcessingtrue\manaNext}% 0-9 case
\hrule\medskip
\mana{X1 2W/UB R /G}
\medskip\hrule\medskip
\mana{X1 2W/UB s/SS 14 1 R /G XZ}
\medskip\hrule\medskip
Run Code Online (Sandbox Code Playgroud)
这里\xe2\x80\x99是我最终在TeX/LaTeX中输入MTG mana的方法:
\n\n\n% http://www.tug.org/TUGboat/Articles/tb28-1/tb88glister.pdf\n\n\\newif\\if@mtg@digit\n\n\\def\\@mtg@testdigit#1{% lame, I know, but nothing else worked\n \\@mtg@digitfalse%\n \\def\\@mtg@tmp{0}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{1}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{2}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{3}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{4}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{5}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{6}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{7}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{8}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n \\def\\@mtg@tmp{9}\\ifx\\@mtg@tmp#1\\@mtg@digittrue\\fi%\n }\n\n\n\\catcode`\\^^G=12\n\n\\newcommand*{\\@mtg@loop}[2]{%\n \\let\\@mtg@callback=#1%\n \\def\\@mtg@string{#2}%\n \\ifx\\@mtg@string\\@empty%\n \\else%\n \\@@mtg@loop#2^^G%\n \\fi%\n}\n\n\\def\\@@mtg@loop#1#2^^G{%\n \\def\\@mtg@car{#1}%\n \\def\\@mtg@cdr{#2}%\n \\ifx\\@mtg@car\\@empty%\n \\let\\@mtg@next=\\@gobble%\n \\else%\n \\@mtg@callback{#1}%\n \\ifx\\@mtg@cdr\\@empty%\n \\let\\@mtg@next=\\@gobble%\n \\else%\n \\let\\@mtg@next=\\@@mtg@loop%\n \\fi%\n \\fi%\n \\@mtg@next#2^^G%\n}\n\n\\catcode`\\^^G=15\n\n% these are meant to be redefined\n\\def\\mtg@mana#1{(\\MakeUppercase{#1})}\n\\def\\mtg@mana@colored#1{\\mtg@mana{#1}}\n\\def\\mtg@mana@colorless#1#2{\\mtg@mana{#1#2}}\n\\def\\mtg@mana@hybrid#1#2{\\mtg@mana{#1/#2}}\n\n\\gdef\\@mtg@terminator{.}\n\\gdef\\@mtg@slash{/}\n\\let\\@mtg@a=\\@mtg@terminator\n\\let\\@mtg@b=\\@mtg@terminator\n\n\\def\\@mtg@doChar#1{%\n \\gdef\\@mtg@c{#1}%\n \\ifx\\@mtg@a\\@mtg@terminator%\n \\else%\n \\ifx\\@mtg@b\\@mtg@slash%\n \\mtg@mana@hybrid{\\@mtg@a}{\\@mtg@c}%\n \\let\\@mtg@b=\\@mtg@terminator%\n \\let\\@mtg@c=\\@mtg@terminator%\n \\else%\n \\@mtg@testdigit\\@mtg@a\\if@mtg@digit%\n \\@mtg@testdigit\\@mtg@b\\if@mtg@digit%\n \\ifx\\@mtg@c\\@mtg@slash%\n \\mtg@mana@colorless{}{\\@mtg@a}%\n \\else%\n \\mtg@mana@colorless{\\@mtg@a}{\\@mtg@b}%\n \\let\\@mtg@b=\\@mtg@terminator%\n \\fi%\n \\else%\n \\mtg@mana@colorless{}{\\@mtg@a}%\n \\fi%\n \\else%\n \\mtg@mana@colored{\\@mtg@a}%\n \\fi%\n \\fi%\n \\fi%\n \\let\\@mtg@a=\\@mtg@b%\n \\let\\@mtg@b=\\@mtg@c%\n}\n\n\\newcommand{\\mana}[1]{%\n\\let\\@mtg@a=\\@mtg@terminator%\n\\let\\@mtg@b=\\@mtg@terminator%\n\\@mtg@loop{\\@mtg@doChar}{#1\\@mtg@terminator\\@mtg@terminator}}\nRun Code Online (Sandbox Code Playgroud)\n
| 归档时间: |
|
| 查看次数: |
3107 次 |
| 最近记录: |