Seite 1 von 1

Makroexpansion bei \write

Verfasst: Di 11. Apr 2023, 10:34
von Rolli
Hallo, ich verzweifele gerade. Irgendwie verstehe ich das Thema Makroexpansion nicht.

Ich möchte an einer Stelle
3 + 5 = ?
und an einer anderen Stelle
3 + 5 = 8
stehen haben - das "3 + 5 =" aber nicht zweimal schreiben. Mein Ansatz:
\def\Loesung{=?}
$3+5\Loesung{8}$
und
\def\Loesung{=#1}
$3+5\Loesung{8}$
Das nachstehende MWE zeigt meine Versuche (alles auskommentiert, weil nichts funktioniert). Aus der Beschreibung im TexBook Kapitel 20 werde ich leider nicht schlau.
\documentclass{article}

% Workaround aus dem TexBook, Appendix D: Dirty Tricks, Seite 373

\long\def\unexpandedwrite#1#2{\def\finwrite{\write#1}%
{\aftergroup\finwrite\aftergroup{\sanitize#2\endsanity}}}
\def\sanitize{\futurelet\next\sanswitch}
\def\sanswitch{\let\n@xt\endsanity \ifx\next\endsanity
\else\ifcat\noexpand\next\stoken\aftergroup\space\let\n@xt=\eat
\else\ifcat\noexpand\next\bgroup\aftergroup{\let\n@xt=\eat
\else\ifcat\noexpand\next\egroup\aftergroup}\let\n@xt=\eat
\else\let\n@xt=\copytok\fi\fi\fi\fi \n@xt}
\def\eat{\afterassignment\sanitize \let\next= }
\long\def\copytok#1{\ifcat\noexpand#1\relax\aftergroup\noexpand\fi
\ifcat\noexpand#1\noexpand~\aftergroup\noexpand\fi
\aftergroup#1\sanitize}
\def\endsanity\endsanity{}

\def\Loesung{=?}

\newcommand{\Aufgabe}[1]{
\def\Loesung{=?}
#1
%\immediate\write\myFile{\string\def\Loesung{=#1}}
%\immediate\write\myFile{\noexpand\def\Loesung{=#1}}
%\immediate\write\myFile{\unexpanded{\def\Loesung{=#1}}}
%\immediate\write\myFile{\unexpandedwrite\def\Loesung{=#1}} % Gibt schon beim Übersetzen einen Fehler
%\immediate\write\myFile{\meaning\def\Loesung{=#1}}
\immediate\write\myFile{#1}
}

\begin{document}

\newwrite\myFile
\immediate\openout\myFile=\jobname.aufgabe

\Aufgabe{$3+5\Loesung{8}$}

\immediate\closeout\myFile

%\input{\jobname.aufgabe} % Keiner meiner Versuche funktioniert ...

\end{document}
Weiß jemand einen Rat?

Gruß vom Rolli

Re: Makroexpansion bei \write

Verfasst: Sa 15. Apr 2023, 18:35
von u_fischer
ich habe keine Ahnung, was du eigentlich erreichen willst. Aber irgendwelche dirty tricks aus dem TeXbook brauchst du sicher nicht. Wir haben 2023 und alle Engines kennen \unexpanded und \detokenize und LaTeX kann toc-Einträge und ähnliches auch ohne sowas schreiben.

Re: Makroexpansion bei \write

Verfasst: Di 18. Apr 2023, 13:15
von Rolli
Hallo Ulrike,

ich möchte in meiner LaTeX-Quelle schreiben: (MWE Zeile 37)
\Aufgabe{$3+5\Loesung{8}$}
Ausgegeben werden soll "3+5=?".

Außerdem soll in ein temporäres File geschrieben werden
$3+5=8$
Das temporäre File wird im MWE Zeile 35 geöffnet.

Das Makro \Aufgabe, welches das tun soll, ist in Zeile 19 bzw. 21 ... 30. Die auskommentierten write's zeigen meine Versuche, um aus
\Aufgabe{$3+5\Loesung{8}$}
dieses zu machen:
$3+5=8$
Und genau das gelingt mir nicht; vermutlich, weil ich aus den zitierten Passagen des TeXbook nicht schlau werde ...

Gruß vom Rolli

Re: Makroexpansion bei \write

Verfasst: Di 18. Apr 2023, 15:30
von u_fischer
Es gibt keinen Grund warum du beim Schreiben das \Loesung entfernen solltest. Möglich ist es, aber es stört doch nicht.
\documentclass{article}

\newwrite\aufgabenfile
\immediate\openout\aufgabenfile=\jobname.aufgabe
\newcommand\Loesung[1]{#1}
\newcommand\Aufgabe[1]{% 
  \begingroup
  \def\Loesung##1{\mathrm{??}}%
  \immediate\write\aufgabenfile{\unexpanded{#1\par}}
  #1
  \endgroup
}

\begin{document}

\Aufgabe{$3+5=\Loesung{8}$}

\Aufgabe{$4-5=\Loesung{-1}$}

\immediate\closeout\aufgabenfile
\input{\jobname.aufgabe}

\end{document}

Re: Makroexpansion bei \write

Verfasst: Mi 19. Apr 2023, 21:44
von Rolli
Danke, Ulrike. Dass \def lokal wirkt, hatte ich nicht im Hinterkopf. Das löst meine Aufgabe, aber leider nicht mein Verständnisproblem.

Wenn irgendwer ein gutes Tutorial zum Thema Expansion kennt (also eine vollständige und für einen Nicht-Mathematiker verständliche Darstellung, was \expandafter, \noexpand, \unexpanded, \string und Konsorten tun), bitte posten.

Gruß vom Rolli