我希望能夠改變內容節點,從自製參數列表到實際文字。
例如,我想建立如下樹:
\documentclass{standalone}
\usepackage{forest}
\begin{document}
\begin{forest}
[9;12;4
[31;21]
[3
[14]
[7;21;3]
]
]
\end{forest}
\end{document}
將被格式化為這樣:
基本上,根據參數的數量(由半列分隔),我想以不同的方式格式化最終內容:
- 有 1 個參數,格式為“#1 is the one”
- 有 2 個參數,格式為“with #1[#2]”
- 有 3 個參數,格式為“$#2 \geq #1$ for #3 case”
到目前為止,我設法將每個節點的內容分割為分割選項,但我沒有成功地知道我實際上有多少個,也沒有成功地訪問它們中的每一個。
我正在尋找的是這樣的:
before typesetting nodes={
for tree={
split option={content}{;}{params},
if {length(params) = 1}{content=params[1] is the one}{
if {length(params) = 2}{content=with params[1][params[2]]}{
if {length(params} = 3}{content=$params[2] \geq params[1]$ for params[3] cases}
{}
}
}
}
}
PS:我嘗試以這種方式做到這一點的原因是因為我需要創建很多具有相同節點格式的大樹。從編寫者的角度來看,選擇每個節點的參數並保持格式分開要容易得多,尤其是在以後必須更改它的情況下。
答案1
split option
(和其他split
鍵)“zip”給定的“指令”鍵列表(它們的#3
)和“參數”列表(在選項情況下,選項的分割值作為它們給出#1
)。因此,選項的各個部分可以由不同的鍵來處理。
\documentclass{standalone}
\usepackage{forest}
\forestset{
declare toks register=param1,
declare toks register=param2,
declare toks register=param3,
gobble/.style={},
my split/.style={
param1={},
param2={},
param3={},
split option={content}{;}{param1,param2,param3,gobble},
if param2={}{
content'/.process=Rw1{param1}{##1 is the one}
}{
if param3={}{
content'/.process=R2w2{param1}{param2}{with ##1[##2]}
}{
content'/.process=R3w3{param1}{param2}{param3}{$##2 \geq ##1$ for ##3 cases}
}
}
}
}
\begin{document}
\begin{forest} delay={for tree=my split}
[9;12;4
[31;21]
[3
[14]
[7;21;3]
]
]
\end{forest}
\end{document}
答案2
我不確定是否split option
適用於不同維度的清單。 (我不確定真的意味著我不知道。)但是,您可以使用 分割內容xstring
。 (我還加了一個刪除虛假空格的補丁;在 pgf 的更高版本中,將不再需要此操作。
\documentclass{standalone}
\usepackage{forest}
\usepackage{xstring}
\makeatletter
% remove the stray space https://tex.stackexchange.com/a/513549
\patchcmd{\pgfutilsolvetwotwoleqfloat}
{ \noexpand\pgfmathfloatdivide@}
{\noexpand\pgfmathfloatdivide@}
{}{}
\makeatother
\begin{document}
\begin{forest}
before typesetting nodes={
for tree={
content/.wrap value={\StrCount{#1}{;}[\mydim]%
\StrSubstitute{#1}{;}{,}[\mytemp]%
\ifcase\mydim
\pgfmathsetmacro{\myone}{{\mytemp}[0]}\myone\ is the one
\or
\pgfmathsetmacro{\myone}{{\mytemp}[0]}%
\pgfmathsetmacro{\mytwo}{{\mytemp}[1]}%
{with \myone[\mytwo]}
\or
\pgfmathsetmacro{\myone}{{\mytemp}[0]}%
\pgfmathsetmacro{\mytwo}{{\mytemp}[1]}%
\pgfmathsetmacro{\mythree}{{\mytemp}[2]}%
{$\mytwo\geq\myone$ for \mythree\ cases}
\fi}}}
[9;12;4
[31;21]
[3
[14]
[7;21;3]
]
]
\end{forest}
\end{document}
或者也可以使用字串的版本。
\documentclass{standalone}
\usepackage{forest}
\usepackage{xstring}
\makeatletter
% remove the stray space https://tex.stackexchange.com/a/513549
\patchcmd{\pgfutilsolvetwotwoleqfloat}
{ \noexpand\pgfmathfloatdivide@}
{\noexpand\pgfmathfloatdivide@}
{}{}
\makeatother
\def\pfttwo#1;#2|{\def\myone{#1}\def\mytwo{#2}}%
\def\pftthree#1;#2;#3|{\def\myone{#1}\def\mytwo{#2}\def\mythree{#3}}%
\begin{document}
\begin{forest}
before typesetting nodes={
for tree={
content/.wrap value={\StrCount{#1}{;}[\mydim]%
\ifcase\mydim
\pgfmathsetmacro{\myone}{#1}\myone\ is the one
\or
\pfttwo#1|%
{with \myone[\mytwo]}
\or
\pftthree#1|%
{$\mytwo\geq\myone$ for \mythree\ cases}
\fi}}}
[9;12;4
[31;21]
[3
[14]
[7;21;3]
]
]
\end{forest}
\end{document}