Conseils pour jouer au golf dans TeX / LaTeX

28

Quels conseils les gens ont-ils pour jouer au golf dans TeX / LaTeX? Veuillez poster un conseil par réponse, chacun au moins quelque peu spécifique à TeX / LaTeX.


Contexte: J'ai remarqué cette réponse et il n'y a pas de question de conseils pour TeX / LaTeX, donc je crée celle-ci. Il y a un certain chevauchement avec les conseils de questions plus étroits pour jouer au golf dans TikZ (car TikZ est un package de macro spécifique au-dessus de TeX / LaTeX): les réponses à cette question s'appliqueront probablement également là-bas, mais pas l'inverse.

ShreevatsaR
la source
Comment jouer au golf sans langage de programmation?
The Great Duck
1
@TheGreatDuck Très mal :-)
ShreevatsaR
@TheGreatDuck En fait, TeX est un langage de programmation, même s'il n'est généralement utilisé que comme un langage typographique.
gvgramazio

Réponses:

15

Considérez les macros LaTeX internes plutôt que celles documentées

Par exemple, \romanest une macro LaTeX documentée qui fonctionne sur les compteurs LaTeX. Pour 42devenir, XLIVil faudrait utiliser quelque chose comme

\newcounter{z}
\setcounter{z}{42}
\roman{z}

Au lieu de cela, en recherchant comment \romanest implémenté (utilisé \show\romanpour l'obtenir de manière interactive, au lieu de lire les fichiers source), on peut voir qu'il est implémenté en termes d'une macro utile appelée \@roman, et plutôt l'utiliser directement:

\catcode`@11
\@roman{42}

\catcode`@11est l'écriture golfique \makeatletter(voie propre dans LaTeX) ou \catcode`\@=11(voie propre dans TeX simple). Il n'est nécessaire qu'une seule fois au début, après cela, vous pouvez utiliser des noms de macro contenant @.

ShreevatsaR
la source
13

~peut être utilisé comme macro (tout comme les autres caractères actifs)

Exemple

Avant:

\def\a{...some definition...} ... use \a...

Après:

\def~{...some definition...} ... use ~...

Explication : Généralement, les macros dans TeX sont des «séquences de contrôle»: vous pouvez définir \somethingou \a. Mais vous pouvez aller encore plus court, en utilisant un personnage actif. Le seul caractère actif présent par défaut (en plain TeX / LaTeX) est ~(utilisé pour les «cravates», c'est-à-dire défini comme \penalty \@M \en plain TeX (une pénalité de 10000 suivie d'un espace), et comme \nobreakspace {}en LaTeX). Mais rien ne vous empêche de le redéfinir pour le but dont vous avez besoin.

En outre : vous pouvez faire la même chose avec n'importe quel autre personnage en définissant son code de chat sur \active(13). Par exemple, faire Zun caractère actif a un « coût » de 12 octets: \catcode`Z13. Ensuite, vous pouvez utiliser simplement Zpartout au lieu d'une macro comme \z. Pour certains caractères qui commencent par une signification particulière, l'approche de retour direct ne fonctionne pas et vous avez besoin d'un caractère de plus: \catcode`\Z13ou \catcode90=13.

ShreevatsaR
la source
9

\def peut correspondre à des motifs fixes

Disons que vous l'avez fait \def\a #1 #2 {...some definition here...}. Ensuite, lorsque vous l'appelez sur une chaîne comme \a Act42, Scene26, à l'intérieur de la macro, les arguments peuvent être affectés comme # 1 <- Act42,, # 2 <- Scene26et vous devrez alors faire un travail supplémentaire pour extraire les parties pertinentes. Au lieu de cela, on pourrait directement écrire

\def\a Act#1, Scene#2 {...some definition here...}

puis l'appeler comme \a Act42, Scene26définirait directement # 1 <- 42et # 2 <- 26.

(Il s'agit essentiellement de la définition de \def, mais il est facile d'oublier car on ne le fait généralement pas dans LaTeX, préférant passer des arguments {}comme s'il s'agissait d'appels de fonction.)

ShreevatsaR
la source
8

Choisir entre TeX simple et LaTeX

Beaucoup peut être dit à ce sujet, mais en bref, comparez un document TeX ordinaire typique qui imprime "Bonjour" avec un document LaTeX typique pour la même chose:

Hello
\bye

contre

\documentclass{article}
\begin{document}
Hello
\end{document}

Le "coût" de LaTeX (wrt code golf) est évident; le «bénéfice» est bien sûr que LaTeX est livré avec une bibliothèque de nombreuses macros et packages pré-écrits, dont certains peuvent être utiles pour la tâche à accomplir.

ShreevatsaR
la source
J'étais coincé à utiliser LaTeX à cause de \@Roman(faire fonctionner les majuscules en clair coûterait beaucoup d'octets) - mais le TeX simple serait souvent plus court.
Chris H
8

\input ... est plus court que \usepackage{...}

Par exemple, vous pouvez écrire

\input color

au lieu de

\usepackage{color}

ce qui représente 6 octets de moins.

Fatalize
la source
8
Il est utile de souligner cependant que cela \usepackagedevient plus efficace à mesure que le nombre de packages que vous incluez augmente. Étant donné que vous pouvez utiliser plusieurs packages avec une seule \usepackageinstruction, mais que \inputvous avez besoin d'un pour chaque package, si vous utilisez 3 packages ou plus, \usepackagedevient la meilleure option.
Wheat Wizard
7

Si vous utilisez LaTeX, utilisez un courtdocumentclass (idée de Chris H )

Au lieu de commencer avec le typique

\documentclass{article}

on peut choisir des classes de documents plus courtes comme bookou même

\documentclass{ecv}

ou

\documentclass{tui}
ShreevatsaR
la source
Vous devez vous rappeler de rester dans les spécifications de la question, articlepar défaut numérote ses pages, cela peut être considéré comme une sortie supplémentaire. Peut-être qu'une méta-question est pour déterminer quelles classes de documents devraient être autorisées.
Wheat Wizard
@WheatWizard Bon point. Je pense que la question individuelle peut être de savoir si les numéros de page sont considérés comme une sortie supplémentaire.
ShreevatsaR
Je pense qu'une classe minimale serait une bonne idée - un nom d'une seule lettre et pas de numérotation des pages
Chris H
J'ai mis en place un g.clsqui est juste article.clsavec \pagenumbering{gobble}mais comme github est en panne, je ne peux pas le mettre pour l'instant
Chris H
g.cls
Chris H
7

La création d'un environnement appelé myenvironmentgénère les commandes \myenvironmentet \endmyenvironment. Ceux-ci sont utilisés en interne pour commencer et terminer l'environnement. Dans certains cas, ils peuvent être utilisés comme raccourcis. Par exemple, au lieu de

\begin{itemize}
\item abc
\end{itemize}

on peut faire

\itemize
\item abc
\enditemize

Non pris en charge, pas fiable, ne fonctionne pas dans tous les cas, utilisez à vos risques et périls, etc. etc.

Ian Thompson
la source
Bienvenue sur le site!
DJMcMayhem
3
Vous pouvez souvent le faire \itemize{...}pour encore plus d'économies.
Wheat Wizard
4

\usepackage{packagea,packageb,packagec} fonctionne, tant que vous ne passez pas d'options aux packages.

Chris H
la source
4

Exécutez les lignes ensemble. Les sauts de ligne sont rarement nécessaires dans LaTeX / TeX, par rapport à de nombreux langages de forme longue.

Chris H
la source
3

Certaines macros dont vous pourriez vous attendre à avoir besoin d'accolades autour de leurs arguments ne le font pas, en particulier lorsqu'elles sont utilisées dans une autre macro avec #1des arguments de style.

La plupart des macros n'ont besoin d'accolades que s'il y a plus d'un jeton (caractère ou séquence de contrôle) dans l'argument.

\mymacro1          % equivalent to \mymacro{1}
\mymacro{12}       % equivalent to \mymacro{12}
\mymacro a         % equivalent to \mymacro{a}
\mymacro{ab}       % equivalent to \mymacro{ab}
\mymacro\foo       % equivalent to \mymacro{\foo}
\mymacro{\foo x}   % equivalent to \mymacro{\foo x}
Chris H
la source
3

Si vous devez utiliser plusieurs fois la même macro avec un nom long, vous pouvez utiliser \letpour définir un alias plus court.

\let\a\mymacrowithalongname
\a{foo}\a{bar}\a{qux}

Cela économise deux octets \def\a{\mymacrowithalongname}si vous n'avez pas besoin de plusieurs jetons dans la définition.

Au lieu d'un nom de macro, vous pouvez avoir un caractère actif à enregistrer sur les barres obliques inverses.

Notez que \letcela ne fonctionne pas seulement avec les noms de macro mais aussi avec les primitives intégrées. Par exemple, si vous utilisez beaucoup de \ifnum ... \ficonstructions dans votre code, définir \let\i\ifnumet utiliser à la place \i ... \fipourrait vous faire économiser quelques octets. Cela fonctionne même pour \letlui - même: \let\l\let.

Gilles 'SO- arrête d'être méchant'
la source
3

Utilisez judicieusement les groupes locaux {...}

Comme indiqué dans cette réponse , les caractères actifs comme ~peuvent être utilisés comme nom de macro. Malheureusement, ~c'est le seul caractère actif par défaut, et changer le catcode pour un autre caractère coûte cher: \catcode`!13prend 12 octets. Si la nouvelle définition de macro n'est nécessaire que dans une petite région de votre code, les groupes locaux peuvent être une solution.

Lorsque TeX entre dans un nouveau groupe local ouvert par {, il crée un nouveau niveau de regroupement sur la pile de sauvegarde interne. Cela signifie que toutes les macros et tous les registres actuels sont enregistrés. Toutes les modifications qui y sont apportées (sauf si elles sont explicitement marquées comme \global) ne sont désormais actives que jusqu'à la fermeture du groupe }. Cela signifie qu'il ~peut être redéfini au sein d'un groupe, utilisé avec la nouvelle définition, et l'ancienne définition sera automatiquement restaurée une fois le groupe terminé.

Voici un exemple:

\def~{abc}
~ -- {\def~{123}~} -- ~

Cette sorties

abc - 123 - abc

Un effet secondaire intéressant de ce mécanisme de regroupement est que les anciennes valeurs sont toujours disponibles à l'intérieur du groupe jusqu'à ce qu'elles y soient modifiées. Pour illustrer cela, imaginez que nous voulons imprimer un certain nombre de caractères en fonction de la valeur d'un compteur, les remplir avec des espaces jusqu'à une longueur fixe et continuer avec la valeur du compteur d'origine. Cela pourrait être réalisé par les moyens suivants:

\newcount\x
\x=3
Print a char \the\x\ times,
{\x=-\x \advance\x 10 pad with \the\x\ spaces,}
and go on with x=\the\x.

qui sort

Imprimez un caractère 3 fois, complétez avec 7 espaces et continuez avec x = 3.

Ce comportement de regroupement est particulièrement important si vous souhaitez utiliser les macros standard de TeX pour les boucles \loop ... \repeatimbriquées. Ces macros définissent des commandes internes et les utilisent pour déterminer comment procéder. Les imbriquer sans mettre la boucle intérieure entre accolades confondra les commandes internes et conduira à un comportement inattendu.

siracusa
la source
1

L'avancement des compteurs, tels que

\advance\u by 1
\multiply\u by 3
\divide\u by 2

fonctionnent également comme

\advance\u1        % \u = \u + 1
\advance\u-1       % \u = \u - 1
\multiply\u3       % \u = \u * 3
\multiply\u\u      % \u = \u * \u
\divide\u2         % \u = \u / 2

Le même principe fonctionne également pour l'initialisation:

\newcount\u\u1

met le compteur \ u à 1.

Notez que ceux-ci ont besoin d'un caractère d'espacement (saut de ligne ou espace) après eux (ou un \relax, mais l'espace fait de même) de sorte que la commande suivante ne sera pas ignorée. Par exemple,

\u1\the\u

n'imprime PAS \ u, mais ignore la \thecommande.

Simon Klaver
la source
1

\enddocumentau lieu d' \end{document}enregistrer deux caractères

sheß
la source
Ne semble pas fonctionner pour \begin{document}=> \documentbien
sheß