C'è un modo per verificare se un'etichetta è già definita in LaTeX?
Domanda
Ho modificato la domanda dopo la risposta di David Hanak (grazie a proposito!). Ha aiutato con la sintassi, ma sembra che all'inizio non stavo usando la funzione giusta.
Fondamentalmente quello che voglio è lasciare che il compilatore ignori più definizioni di una determinata etichetta e usi solo il primo. Per farlo, ho pensato di fare qualcosa del genere:
\makeatletter \newcommand{\mylabel}[1]{ \@ifundefined{#1}{\label{#1}}{X} } \makeatother
Questo non funziona però, perché la prima opzione è sempre scelta (non importa se l'etichetta è definita o meno). Penso che \ @ifundefined (e il suggerito \ ifundefined) funzionano solo per i comandi e non per le etichette, ma non so molto su LaTeX. Qualsiasi aiuto con questo sarebbe fantastico! Grazie!
Aggiornamento molto più tardi: Ho contrassegnato la risposta di David Hanak come la risposta corretta alla mia domanda, ma non è una soluzione completa, sebbene mi abbia davvero aiutato. Il problema è, penso, ma non sono uno specialista, che anche se il codice di David verifica se un'etichetta è definita, funziona solo quando l'etichetta è stata definita in una corsa precedente (cioè è nel file .aux). Se due \ mylabels con lo stesso nome sono definiti nella stessa esecuzione, il secondo verrà comunque definito. Inoltre, anche se riuscirai a ovviare a questo, LaTeX utilizzerà la prima etichetta definita in ordine cronologico e non necessariamente la prima nel testo. Comunque, di seguito è la mia soluzione rapida e sporca. Utilizza il fatto che i contatori sembrano essere definiti immediatamente.
\newcommand{\mylabel}[1]{% \@ifundefined{c@#1}{% \newcounter{#1}% \setcounter{#1}{0}% }{}% \ifthenelse{\value{#1} > 0}{}{% \label{#1}% \addtocounter{#1}{1}% }% }
Non sono sicuro che sia necessario inizializzare il contatore su 0, poiché sembra un probabile default, ma non sono riuscito a trovare se fosse così, quindi sono solo al sicuro. Inoltre, utilizza il pacchetto 'ifthen', che non sono sicuro sia necessario.
Soluzione
@
è un personaggio speciale in LaTeX. Per rendere sintatticamente corretta la tua dichiarazione, dovrai aggiungere altre due righe:
\makeatletter
\newcommand{\mylabel}[1]{
\@ifundefined{#1}{\label{#1}}{X}
}
\makeatother
La prima riga trasforma \ifundefined
in una lettera normale, l'ultima riga ne inverte l'effetto.
Aggiornamento: potresti anche dare un'occhiata al " plain " \def\newlabel{\@newl@bel r}
Macro LaTeX .
Aggiornamento 2
Okay, ho fatto delle ricerche per capire la risposta al problema reale . Il fatto è che la definizione di un'etichetta non crea una macro con quel nome; antepone un " r @ " ad esso. Quindi prova quanto segue:
\makeatletter
\newcommand{\mylabel}[1]{
\@ifundefined{r@#1}{\label{#1}}{X}
}
\makeatother
Per ulteriori dettagli tecnici, fare riferimento alla riga 3863 di latex.ltx nella distribuzione LaTeX (dove dice <=>).
Altri suggerimenti
Anche io non sono un esperto di LaTeX, tuttavia dopo un giorno di tentativi e ricerche su Internet il seguente ha funzionato per me. Ho usato un contatore fittizio per risolvere il problema. Speriamo che questo aiuti, a quanto pare non molte persone lo stanno cercando.
\newcommand{\mylabel}[1]{
\ifcsname c@#1\endcsname%
\else%
\newcounter{#1}\label{#1}%
\fi%
}
Di Victor Eijkhout, " TeX di Topic " ;, p.143:
\def\ifUnDefinedCs#1{\expandafter\ifx\csname#1\endcsname\relax}
Questo può essere usato per verificare se un'etichetta è definita; in caso contrario, l'etichetta viene stampata:
\newcommand{\myautoref}[1]{\ifUnDefinedCs{r@#1}{\color{magenta}\IDontKnow\{#1\}}\else\autoref{#1}\fi}