Есть ли способ проверить, определена ли метка уже в LaTeX?

StackOverflow https://stackoverflow.com/questions/495841

  •  20-08-2019
  •  | 
  •  

Вопрос

Я отредактировал вопрос после ответа Дэвида Ханака (кстати, спасибо!).Он помог с синтаксисом, но, похоже, я с самого начала использовал не ту функцию.

По сути, я хочу, чтобы компилятор игнорировал несколько определений определенной метки и просто использовал первое.Чтобы сделать это, я подумал, что просто сделаю что-то вроде этого:

    \makeatletter
    \newcommand{\mylabel}[1]{
        \@ifundefined{#1}{\label{#1}}{X}
    }
    \makeatother

Однако это не работает, потому что всегда выбирается первый вариант (не имеет значения, определена метка или нет).Я думаю, что \@ifundefined (и предлагаемый \ifundefined) работают только для команд, а не для меток, но я не очень много знаю о LaTeX.Любая помощь в этом была бы замечательной!Спасибо!

Гораздо более позднее обновление:Я отметил ответ Дэвида Ханака как правильный на мой вопрос, но это не полное решение, хотя оно действительно помогло мне.Проблема в том, я думаю, но я не специалист, что, хотя код David проверяет, определена ли метка, он работает только тогда, когда метка была определена в предыдущем запуске (т. Е.находится в файле .aux).Если две метки \mylabels с одинаковым именем определены в одном и том же запуске, вторая все равно будет определена.Кроме того, даже если вам удастся обойти это, это заставит LaTeX использовать первую метку, которую вы определили в хронологическом порядке, и не обязательно первую в тексте.В любом случае, ниже приведено мое быстрое и грязное решение.Он использует тот факт, что счетчики, похоже, определяются сразу.

\newcommand{\mylabel}[1]{%
    \@ifundefined{c@#1}{%
        \newcounter{#1}%
        \setcounter{#1}{0}%
    }{}%
    \ifthenelse{\value{#1} > 0}{}{%
        \label{#1}%
        \addtocounter{#1}{1}%
    }%
}

Я не уверен, необходимо ли инициализировать счетчик равным 0, поскольку это кажется вероятным значением по умолчанию, но я не смог найти, так ли это, поэтому я просто перестраховываюсь.Кроме того, при этом используется пакет 'ifthen', который, я не уверен, необходим.

Это было полезно?

Решение

@ это специальный символ в LaTeX.Чтобы сделать ваше объявление синтаксически корректным, вам придется добавить еще две строки:

\makeatletter
\newcommand{\mylabel}[1]{
    \@ifundefined{#1}{\label{#1}}{X}
}
\makeatother

Первая строка поворачивается @ в обычном письме последняя строка меняет свое действие на обратное.

Обновить: Возможно, вы также захотите взглянуть на "равнину" \ifundefined Латексный макрос.

Обновление 2

Хорошо, я провел кое-какие исследования, чтобы найти ответ на реальный проблема.Дело в том, что определение метки не создает макрос с таким именем;к нему добавляется буква "r@".Итак, попробуйте следующее:

\makeatletter
\newcommand{\mylabel}[1]{
    \@ifundefined{r@#1}{\label{#1}}{X}
}
\makeatother

Для получения более технических сведений обратитесь к строке 3863 latex.ltx в вашем дистрибутиве LaTeX (где говорится \def\newlabel{\@newl@bel r}).

Другие советы

Я также не специалист по LaTeX, однако после одного дня попыток и поиска в Интернете у меня сработало следующее.Я использовал фиктивный счетчик, чтобы решить проблему.Надеюсь, это поможет, по-видимому, не многие люди ищут это.

\newcommand{\mylabel}[1]{
    \ifcsname c@#1\endcsname%
    \else%
        \newcounter{#1}\label{#1}%
    \fi%
}

Виктор Эйкхаут, "Текст по темам", стр.143:

\def\ifUnDefinedCs#1{\expandafter\ifx\csname#1\endcsname\relax} 

Это может быть использовано для проверки того, определена ли метка;если нет, то этикетка будет напечатана:

\newcommand{\myautoref}[1]{\ifUnDefinedCs{r@#1}{\color{magenta}\IDontKnow\{#1\}}\else\autoref{#1}\fi} 
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top