I'd like to know how to create a macro that can append new elements/items to a macro list (token list) BUT also adds {
and }
around each added item.
Example I'd like it to save each new item like this:
\appendtocslist{tokenlist}{newitem}
yields {newitem}
in the list.
Why Because I can easily parse the list with \readcslist
.
I am not sure if also separating each value with a comma (or some other separator) is necessary.
Append to Command Sequence (CS) List
- Smart enough to initiate a new macro if none exist iwth does not exist.
- It uses csname to allow for dynamic macro names.
- It currently uses a trailing comma character , as a separator/delimiter.
Code
\long\def\appendtocslist#1#2{% #1 = List ID (no backslash) #2=New Item to Append
% I chose this complicated csname form of the list-making because it can accept dynamic csnames using counters
\expandafter\ifx\csname#1\endcsname\relax\expandafter\xdef\csname#1\endcsname{#2,}\else% Macro Existence Check
\expandafter\xdef\csname#1\expandafter\expandafter\expandafter\endcsname
\expandafter\expandafter\expandafter
{\csname #1\endcsname#2,}\fi%Append expansion of #1 with #2, delimit with ,. ^^J appears as newline in terminal or space when typeset and does not work as a delimiter
}%
Code
\documentclass{article}
\usepackage{fontspec}% xelatex
\makeatletter
\long\def\appendtocslist#1#2{% #1 = List ID (no backslash) #2=New Item to Append
% I chose this complicated csname form of the list-making because it can accept dynamic csnames using counters
\expandafter\ifx\csname#1\endcsname\relax\expandafter\xdef\csname#1\endcsname{#2,}\else% Macro Existence Check
\expandafter\xdef\csname#1\expandafter\expandafter\expandafter\endcsname
\expandafter\expandafter\expandafter
{\csname #1\endcsname#2,}\fi%Append expansion of #1 with #2, delimit with ,. ^^J appears as newline in terminal or space when typeset and does not work as a delimiter
}%
\long\def\readcslist#1{%
\@tempcnta=1%
\checknextarg%
}
\long\def\checknextarg{%
% My job is to check for another arg and trigger a recursive cycle.
% for \@ifnextchar to check, so we say \bgroup, which means literal {
% I am only important if there are exactly two args.
\@ifnextchar\bgroup{\recursivecycle}{\advance\@tempcnta1\finalcall}% \@ifnextchar ignores spaces
}
\long\def\recursivecycle#1{%
% My job is to eat each argument recursively until I
% cannot find any more { characters. I ignore spaces.
% If I reach the end, I run whatever is in false area of \@ifnextchar
\advance\@tempcnta by 1% add one for next arg
\@ifnextchar\bgroup{\recursivecycle}{\finalcall}}
\def\finalcall{Total n of args: \the\@tempcnta}
\makeatother
\begin{document}
Hello.
\appendtocslist{mylist}{a}
\appendtocslist{mylist}{b}
\appendtocslist{mylist}{c}
\readcslist{d}{e}{f}
% \expandafter\readargs\expandafter{\mylist} % wouldn't this be nice!%
\end{document}
expl3
. And definitely not absorb items until no more{
are found. This is very dangerous and useless:\readcslist{{a}{b}{c}}
is much simpler and safer.\appendtocslist
and\readcslist
? I see none.