4

I want to create counters in a loop like this (with the packages multido, totcount) :

    \newcounter{compteurChi}% first counter
    \regtotcounter{compteurChi}% define the first counter as a totalcounter
    \newcounter{compteurChii}% second iteration
    \regtotcounter{compteurChii}
    \newcounter{compteurChiii}% third iteration
    \regtotcounter{compteurChiii}

So I write this :

    \newcounter{AuxCounter}
    \renewcommand{\theAuxCounter}{\roman{AuxCounter}}

    \multido{\i=1+1}{3}{%
    \setcounter{AuxCounter}{\i}
    \newcounter{compteurCh\theAuxCounter}
    \regtotcounter{compteurCh\theAuxCounter}
    }

But this does not work : it creates only the last counter compteurChiii. I need to find a way to do this in a loop because I need a lot of counter, and writting it for each is not a solution for me.

I've find answers on the net for problems like mine, but I don't really understand the codes I found to adapt them to definition of counter in a loop.

To be more specific : This example show how it does not work. I use the totcount package to store the bigger value of the counter, and it is not stored for any of them excepted for the last counter created by the loop. As you can see :

\documentclass{article}
\usepackage{multido,totcount}

\newcounter{AuxCounter}
\renewcommand{\theAuxCounter}{\roman{AuxCounter}}

\multido{\i=1+1}{3}{%
\setcounter{AuxCounter}{\i}
\newtotcounter{compteurCh\theAuxCounter}}

\begin{document}

For the first counter : (after compiling two times)

\thecompteurChi

\setcounter{compteurChi}{17}

\thecompteurChi / \total{compteurChi}
\refstepcounter{compteurChi}

\thecompteurChi / \total{compteurChi}
\refstepcounter{compteurChi}

\thecompteurChi / \total{compteurChi}
\refstepcounter{compteurChi}

\thecompteurChi


For the last counter created (the only that works) :

\thecompteurChiii

\setcounter{compteurChiii}{17}

\thecompteurChiii / \total{compteurChiii}
\refstepcounter{compteurChiii}

\thecompteurChiii / \total{compteurChiii}
\refstepcounter{compteurChiii}

\thecompteurChiii / \total{compteurChiii}
\refstepcounter{compteurChiii}

\thecompteurChiii

\end{document}

gives on output :

output

Thank's for help.

4

It's an expansion problem in \regtotcounter; I'll investigate whether it's possible to avoid the cumbersome code, but here's a working solution:

\documentclass{article}
\usepackage{multido,totcount}

\multido{\i=1+1}{3}{%
  \begingroup\edef\x{\endgroup
    \noexpand\newtotcounter{compteurCh\romannumeral\i}%
  }\x
}

\begin{document}

\thecompteurChi

\setcounter{compteurChi}{17}

\thecompteurChi / \total{compteurChi}
\refstepcounter{compteurChi}

\thecompteurChi / \total{compteurChi}
\refstepcounter{compteurChi}

\thecompteurChi / \total{compteurChi}
\refstepcounter{compteurChi}

\thecompteurChi

The third counter:

\thecompteurChiii

\setcounter{compteurChiii}{17}

\thecompteurChiii / \total{compteurChiii}
\refstepcounter{compteurChiii}

\thecompteurChiii / \total{compteurChiii}
\refstepcounter{compteurChiii}

\thecompteurChiii / \total{compteurChiii}
\refstepcounter{compteurChiii}

\thecompteurChiii

\end{document}

You could also go with \newcounter{AuxCounter}, but directly using \romannumeral is more economic.

enter image description here

Where is the problem? The \regtotcounter macro (that's also implicitly called by the command \newtotcounter) delays code to \AtEndDocument:

\def\regtotcounter@mainaux#1{%
%% Create a new counter holding the total number of the actual counter:
  \expandafter\ifx\csname c@#1@totc\endcsname\relax%
      \newcounter{#1@totc}%
      \setcounter{#1@totc}{-1}%
  \fi%
%% At the end of the document write code in the auxiliary file to update the
%% total counter with the value of the actual counter:
  \AtEndDocument{%
    \def\sp{ }%
    \immediate\write\@mainaux{%
      \string\expandafter\string\ifx%
        \string\csname\sp c@#1@totc\string\endcsname\string\relax%
      \string\newcounter{\string #1@totc}%
      \string\fi%
      \string\setcounter{\string #1@totc}{\number\value{#1}}%
    }%
  }%
}

A better version of it would be

\newcommand\regtotcounter@mainaux[1]{%
  \@ifundefined{c@#1@totc}{%
    \newcounter{#1@totc}%
    \setcounter{#1@totc}{-1}%
  }{}%
  \AtEndDocument{%
    \immediate\write\@mainaux{%
      \string\@ifundefined{c@#1@totc}{\string\newcounter{#1@totc}}{}%
      \string\setcounter{#1@totc}{\number\value{#1}}%
    }%
  }%
}

However both versions suffer from the same problem: when #1 is \romannumeral\i it is fully expanded by the immediately executed \newcounter and \setcounter instructions, but not when \romannumeral\i is passed to \AtEndDocument. Thus, at end document, \romannumeral\i will use the value 16, because \i is defined by \chardef\i=16 by the kernel when the font encoding is OT1.

The trick above expands \romannumeral\i before the instructions are performed, so all goes well and the .aux file will have

\@ifundefined{c@compteurChi@totc}{\newcounter{compteurChi@totc}}{}\setcounter{compteurChi@totc}{20}
\@ifundefined{c@compteurChii@totc}{\newcounter{compteurChii@totc}}{}\setcounter{compteurChii@totc}{0}
\@ifundefined{c@compteurChiii@totc}{\newcounter{compteurChiii@totc}}{}\setcounter{compteurChiii@totc}{20}

with my version of the macro or the more convoluted code with the original version.

2

I don't see any real problem with your code. There is \newtotcounter that creates a counter and registers it with totcount in one go, which will save some coding. Here is a complete document showing it working.

\documentclass{article}

\usepackage{multido,totcount}

\newcounter{AuxCounter}
\renewcommand{\theAuxCounter}{\roman{AuxCounter}}

\multido{\i=1+1}{3}{%
\setcounter{AuxCounter}{\i}
\newtotcounter{compteurCh\theAuxCounter}}

\begin{document}

\thecompteurChi

\refstepcounter{compteurChii}

\thecompteurChii

\setcounter{compteurChiii}{17}

\thecompteurChiii

\end{document}

producing

Sample output

  • Thanks but it does not work, I show more precisions on the answer below. – math45 May 15 '15 at 13:12

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.