1

How to define a macro that accepts comma separated arguments, iterates over the arguments and inserts some command or text between the arguments?

E.g. by checking if the current argument is not the first.

I would like to pass \mycommand{a,b,c} and get a \and b \and c.

Here is my example using \author and \and

\documentclass[]{article}

\usepackage{expkv-cs}

\ekvcHash\myauthor{author=,affiliation=,email=,}{% \begin{tabular}{ c } \ekvcValue{author}{#1}\ \ekvcValue{affiliation}{#1} \end{tabular} }

% this macro should have comma separated arguments instead of three fixed arguments \newcommand*{\myauthorslist}[3]{% \author{ \myauthor{#1} \and \myauthor{#2} \and \myauthor{#3} % this should be done by iterating the arguments } }

\begin{document}

\myauthorslist {author={Author1},affiliation={University of City1}} {author={Author2},affiliation={University of City2}} {author={Author3},affiliation={University of City3}}

\title{mytitle} \maketitle

\end{document}

I.e. pass the arguments like the following:

\myauthorslist{
  {author={Author1},affiliation={University of City1}}
  ,{author={Author2},affiliation={University of City2}}
  ,{author={Author3},affiliation={University of City3}}
  % ...
}

UPDATE: What I've tried so far:

\documentclass[]{article}

\usepackage{expkv-cs}

\ekvcHash\myauthor{long author=,long affiliation=}{% \begin{tabular}{ c } \ekvcValue{author}{#1}\ \ekvcValue{affiliation}{#1} \end{tabular} }

\ExplSyntaxOn \NewDocumentCommand \myauthorslist { O{ \and } m } { \clist_use:nn { #2 } { #1 } } \ExplSyntaxOff

\begin{document}

\author{ \myauthorslist{ \myauthor{author={Author1},affiliation={University of City1}}, ,\myauthor{author={Author2},affiliation={University of City2}} ,\myauthor{author={Author3},affiliation={University of City3}} } }

\title{mytitle} \maketitle

\end{document}

The previous is working. But I'd like to non repeat \myauthor and call it like the following:

\author{
  \myauthorslist{
    {author={Author1},affiliation={University of City1}},
    ,{author={Author2},affiliation={University of City2}}
    ,{author={Author3},affiliation={University of City3}}
  }
}

But I don't know how to use \myauthor in \myauthorslist. The following is not working:

\NewDocumentCommand \myauthorslist { O{ \and } m } {
  \clist_use:nn { #2 } { \myauthor{ #1 } } % <- this is not working!
}
wolfrevo
  • 513
  • I'm not sure what the desired syntax is. Do you want this to work as \myauthorslist{{cs list},{cs list},...}? – campa Oct 25 '23 at 09:16
  • @campa yes. I've updated my question – wolfrevo Oct 25 '23 at 09:19
  • In expl3, you can use clists. Does this help? https://tex.stackexchange.com/a/576767/278534 – User23456234 Oct 25 '23 at 09:23
  • @DavidCarlisle: Sorry. I'm not acquainted with those. Would you mind to provide or refer to an example. – wolfrevo Oct 25 '23 at 09:57
  • @User23456234: Yes. Using { O{ \and } m }. But I don't know how to pass \myauthor to \clist_use:nn { #2 } { #1 }. I've tried \clist_use:nn { #2 } { \myauthor{#1} } but it doesn't work. – wolfrevo Oct 25 '23 at 09:59
  • actually you want a clist for the first list then handle each item as keyval (I'd probably have used separate commands rather than the tricky syntax with nested commas having to be hidden by brace groups)\author {author={Author1},affiliation={University of City1}} \author{author={Author2},affiliation={University of City2}} \author{author={Author3},affiliation={University of City3}} – David Carlisle Oct 25 '23 at 10:01
  • @DavidCarlisle: I've updated my question with what I've tried so far – wolfrevo Oct 25 '23 at 10:13
  • Another possibility, without using expl3, could be listofitems package. – Iacobus1983 Oct 25 '23 at 11:50
  • I would recommend using \seq_set_from_clist to fill a sequence from a command which takes a clist as argument. Then you can process the sequence with \seq_use:Nnnn and specify the separators (nnn). First the separator between exact two items, second the separator between multiple items, third the separator only between the last two of multiple items. – lukeflo Oct 25 '23 at 16:23
  • @lukeflo Why not \clist_use:Nnnn? – cfr Oct 26 '23 at 00:28
  • @cfr: AFAIU one advantage of using seq is that it can be indexed when mapping to a function via seq_map_indexed_function. This is very useful if you want to test whether you are on the first item or elsewhere in the sequence. – wolfrevo Oct 26 '23 at 08:06
  • @cfr I'm not sure but if I remember correctly the docs state that seq are faster to process than clists. The mapping could also be interesting for the OP if he wants to use related list entries. – lukeflo Oct 26 '23 at 09:08
  • @lukeflo That's true. There are certainly reasons to turn clists into sequences. But if somebody is just starting out with expl3 (as seems to be the case here) and the job can be done directly with a clist, the direct approach is probably the more straightforward one. Unless the OP needs to do this over and over, the speed difference is likely to be negligible. – cfr Oct 26 '23 at 14:01
  • Latex beginners can probably be classified in two groups: those who have a background in other language(s) and those who not. Most of experienced programmers would expect some features of lists which AFAIK are not available in clist: e.g. indexed and pairwise mapping or filtering. BTW: those could be implemented for clist too. – wolfrevo Oct 26 '23 at 14:34
  • BTW: Following three quotes from the documentation: "Sequences (defined in l3seq) are safer, faster, and provide more features, so they should often be preferred to comma lists", "Almost all operations on comma lists are noticeably slower than those on sequences so converting the data to sequences using \seq_set_from_clist:Nn (see l3seq) may be advisable if speed is important.", and "The sequence data type should thus certainly be preferred to comma lists to store such items." (see https://ctan.math.illinois.edu/macros/latex/contrib/l3kernel/interface3.pdf#page=182) – wolfrevo Oct 26 '23 at 14:38

0 Answers0