3

I need a nested loop to animate PSTricks diagrams. In C# or C or C++, I usually write as follows.

int N=6;
for(int x=0; x<N; x++)
    for(int y=x+1; y<N; y++)
        Console.WriteLine("({0}, {1})",x,y);

I have attempted to do it in TeX as follows, but it does not work. :-)

\documentclass{minimal}
\usepackage{multido}

\newcommand\N{6}
\newcommand\Init{}
\newcommand\Freq{}
\begin{document}
\multido{\ix=0+1}{\N}
{
        \makeatletter
            \renewcommand\Init{\strip@pt\dimexpr\ix pt + 1pt\relax}         
            \renewcommand\Freq{\strip@pt\dimexpr\N pt - \Init pt\relax}
        \makeatother
        \multido{\iy=\Init+1}{\Freq}
        {
                (\ix, \iy)\par
        }
}
\end{document}

How to fix it?

6
\documentclass{minimal}
\usepackage{multido}

\newcommand\N{6}
\begin{document}
\multido{\ix=0+1,\ixB=1+1,\iN=5+-1}{\N}{%
  \multido{\iy=\ixB+1}{\iN}{(\ix, \iy)\endgraf}}
\end{document}

and with a counter:

\documentclass{minimal}
\usepackage{multido}
\newcommand\N{6}
\newcounter{NminusOne}
\setcounter{NminusOne}{\N}\addtocounter{NminusOne}{-1}

\begin{document}
\multido{\ix=0+1,\ixB=1+1,\iN=\theNminusOne+-1}{\N}{%
  \multido{\iy=\ixB+1}{\iN}{(\ix, \iy)\endgraf}}
\end{document}
  • Is there a trick to avoid hard-coding the value 5? – xport Jul 23 '11 at 21:13
  • define two counters for N and NminusOne, then you can use these instead of \N and 5 – user2478 Jul 23 '11 at 21:22
  • @Herbert: It seems useful to define \multido as a long macro. Is there any special reason that \multido isn't a long macro? If not, could you revise it to support \par? – Leo Liu Jul 23 '11 at 21:36
  • @Leo: it is a really old package and only bug fixes will be done. Too many people use it in the meantime, modifications to the code may be dangerous. You can use \endgraf instead and all is fine. – user2478 Jul 23 '11 at 21:48
1

You need to use \edef to expand the macro content. Using \renewcommand simply redefines the macro to the exact same content over and over again. That the \ix and \Init macros have a changing value doesn't matter here. You can't have a paragraph in \multido because it isn't defined \long. So use either \\ or hide the \par in a macro. You need also take care of spaces introduced by line breaks, e.g. after } and {. The \makeatletter and \makeatother macros must be places outside the \multido macro, otherwise it's already to late to change catcodes.

\documentclass{minimal}
\usepackage{multido}

\newcommand\N{6}
\newcommand\Init{}
\newcommand\Freq{}
\newcommand\mypar{\par}
\begin{document}
\makeatletter
\multido{\ix=0+1}{\N}{%
    \edef\Init{\strip@pt\dimexpr\ix pt + 1pt\relax}%
    \edef\Freq{\strip@pt\dimexpr\N pt - \Init pt\relax}%
    \multido{\iy=\Init+1}{\Freq}{%
        (\ix, \iy)\mypar
    }%
}
\makeatother
\end{document}
  • where is the sense to use \dimexpr when the unit is not needed? – user2478 Jul 23 '11 at 20:58
  • Thank you for your answer. Especially introducing me to \edef. It might be used in another scenario in my life. :-) Since Herbert's solution is simpler than yours so I switched the green mark to Herbert's. – xport Jul 23 '11 at 21:01
  • @Herbert: I didn't changed that part of xport's original code, simply fixed the other issues. The code works beside that. – Martin Scharrer Jul 23 '11 at 21:02
  • @xport: That's fine. You shouldn't accept answers right away anyway. – Martin Scharrer Jul 23 '11 at 21:02
0

The following is the simplified version of Herbert's answer.

\documentclass{minimal}
\usepackage{multido}
\newcommand\N{6}


\newcounter{NTemp}
\setcounter{NTemp}{\N}

\begin{document}
\multido{\ix=0+1,\iTemp=1+1}{\N}
{
  \addtocounter{NTemp}{-1}
  \multido{\iy=\iTemp+1}{\theNTemp}
  {
    (\ix, \iy)\endgraf
  }
}
\end{document}
0
\documentclass{minimal}
\usepackage{multido}


\newcommand{\N}{6}
\newcounter{Init}
\newcounter{Freq}
\setcounter{Freq}{\N}
\newcommand\mypar{\par}

\begin{document}
\multido{\ix=0+1}{\N}
{
    \setcounter{Init}{\ix}
    \addtocounter{Init}{1}
    \addtocounter{Freq}{-1}
    \multido{\iy=\value{Init}+1}{\value{Freq}}
    {
        (\ix, \iy)\endgraf
    }
}
\end{document}
  • see edited answer – user2478 Jul 23 '11 at 21:41

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.