7

When writing articles containing math, I would like to have a way to ensure that I am not using an undefined term or symbol. For instance, I want to use the term "simple algebra" only after I define it. For this, I can create a command

\newcommand{\simplealgebra}{simple algebra}

and place it just before the \begin{definition} command in which I define it. On the other hand, if I write another paper, where I use the same term or symbol, I don't want to end up by having duplicate commands, so I want to keep all the commands defined in one place, in the preamble, which possibly I want to share between more documents.

Is there any way to combine the two conditions, namely, to have the command defined in the preamble, but to ensure the usage of the command only from one point in the document body?


Below is a minimal working example, as requested in comments. The example shows how I can use \newcommand to force myself to avoid using a term before being defined with \begin{definition}.

\documentclass{article}%

\newtheorem{theorem}{Theorem}
\newtheorem{definition}[theorem]{Definition}

\begin{document}

...

Some introductory things. Here we don't know what an even number is, and using ``\textbackslash evennumber'' gives error.

%uncomment the following to get an error
%Some text about \evennumber
...

Starting from here, it is allowed to talk about even numbers.
\newcommand{\evennumber}{even number}
\begin{definition}
An {\evennumber} is an integer that is divisible by $2$.
\end{definition}
\end{document}
  • I know how to share a preamble containing definitions of commands.

  • I know how to force the usage of a term after being defined. But to do this, I move the \newcommand from the preamble

  • What I don't know, and I would like to know, is how to keep the \newcommand in the preamble, and yet make possible to use it only starting from a given position in the body of the document.

  • 1
    Could you post a minimal working example (MWE) to further explain what you mean? – jubobs Aug 24 '13 at 18:11
  • I'm not sure to understand. Defining all these custom commands in a file mypreamble.tex and then use \input{mypreamble} in the preamble of your documents is a good solution for you? Or you want those commands defined locally to a specific environment? – karlkoeller Aug 24 '13 at 18:48
  • Which document class are you using and in what way is your definition environment defined? What I take from the question is that she wants to set a flag in the definition environment to indicate that the term has been defined and have the \simplealgebra command check the flag and throw an error if it hasn't been set. Is that a reasonable understanding Cristi? – Scott H. Aug 24 '13 at 18:52
5

One way to do this to define \ActiveXXX which then defines \XXX so that is it useable in the remainder of the document. For example:

\newcommand{\ActicvateEvenNumber}{\def\EvenNumber{even number\xspace}}%

This should be included from an external file so that usage is consistent between them.

Notes:

  • I have used the xspace package to eliminate the need to handle the case of an optional trailing space.
  • I have done something similar a while ago, so should warn you that there are other issues that may be good to think of upfront. Two that comes to mind is the issue of plural versions, and the use of the word at the beginning of a sentence.

Code:

\documentclass{article}
\usepackage{xspace}

%% Include these from an external .sty file:
\newcommand{\ActicvateEvenNumber}{\def\EvenNumber{even number\xspace}}%

\begin{document}

%Test error condition by uncommenting:
%An \EvenNumber is one that is divsible by 2.

\ActicvateEvenNumber
An \EvenNumber is one that is divsible by 2.

\end{document}

A more elegant way would be to have an external file containing two columns with the macro name, and the associated text. Read this file in, with something such as the the datatool package for instance, and then call a macro \ActiveMacro{evennumber} which will then make the \evenmacro available for use for the remainder of the document.

4

Define \defineterm that takes as arguments a control sequence and the corresponding text. We have to use \gdef because the definition may take place inside an environment, so we need also to check for the definability.

\documentclass{article}

\usepackage{amsthm}

\newtheorem{theorem}{Theorem}

\theoremstyle{definition}
\newtheorem{definition}[theorem]{Definition}

\makeatletter
\newcommand{\defineterm}[2]{%
  \@ifdefinable{#1}{\gdef#1{#2}\emph{#2}}}
\makeatother

\begin{document}

Some introductory things. Here we don't know what an even number is, and using 
``\evennumber'' gives error.

Starting from here, it is allowed to talk about even numbers.
\begin{definition}
An \defineterm{\evennumber}{even number} is an integer that is divisible by $2$.
\end{definition}

And here we can talk about an \evennumber{} because we already defined it.
\end{document}

In the example, the first occurrence of \evennumber will result in an error. On the other hand, there's no way to ensure the explicit term “even number” is not used before the definition.

This method has a drawback: it becomes more and more difficult to remember what commands have been defined.


Here is a way to have the definitions in the preamble. The real text is stored in a property list, while the command is temporarily defined to issue an error message.

The definition environment has an optional argument, taking a comma separated list of terms (the control sequence names) that will be legal from that point on.

\documentclass{article}%
\usepackage{amsthm,xparse}

\newtheorem{theorem}{Theorem}
\theoremstyle{definition}
\newtheorem{xdefinition}[theorem]{Definition}

\ExplSyntaxOn
\NewDocumentCommand{\defineterm}{mm}
 {
  \cstoica_defineterm:nn { #1 } { #2 }
 }
\NewDocumentEnvironment{definition}{O{}}
 {
  \cstoica_enable:n { #1 }
  \xdefinition
 }
 {
  \endxdefinition
 }

\prop_new:N \g_cstoica_terms_prop
\tl_new:N \l_cstoica_currentterm_tl

\cs_new_protected:Npn \cstoica_defineterm:nn #1 #2
 {
  \prop_gput:Nnn \g_cstoica_terms_prop { #1 } { #2 }
  \cs_new:cpn { #1 } { \msg_error:nnn { cstoica/terms } { early } { #1 } }
 }

\cs_new_protected:Npn \cstoica_enable:n #1
 {
  \clist_map_inline:nn { #1 } { \cstoica_enableterm:n { ##1 } }
 }
\cs_new_protected:Npn \cstoica_enableterm:n #1
 {
  \prop_get:NnNTF \g_cstoica_terms_prop { #1 } \l_cstoica_currentterm_tl
   { \cs_gset_eq:cN { #1 } \l_cstoica_currentterm_tl }
   { \msg_error:nnn { cstoica/terms } { undefined } { #1 } }
 }

\msg_new:nnnn { cstoica/terms } { early }
 {
  Term~`#1'~not~yet~defined
 }
 {
  You~have~used~`#1'~before~formally~defining~it
 }
\msg_new:nnnn { cstoica/terms } { undefined }
 {
  Undefined~term~`#1'
 }
 {
  The~term~`#1'~is~not~defined,~check~the~name
 }
\ExplSyntaxOff

\defineterm{evennumber}{even number}
\defineterm{integer}{integer number}

\begin{document}

Some introductory things. Here we don't know what an even number is, and using 
``\evennumber'' gives error.


Starting from here, it is allowed to talk about even numbers.
\begin{definition}[evennumber]
An \emph{\evennumber} is an integer that is divisible by $2$.
\end{definition}

And here we can talk about an \evennumber{} because we already defined it.

\begin{definition}[integer,rational]
Here we define an \emph{\integer}, but we get an error about \emph{\rational}.
\end{definition}
\end{document}

The implementation is simpler with giving only the control sequence name, but it would be possible to modify it to require

\defineterm{\evennumber}{even number}

in the preamble and

\begin{definition}[\evennumber]

in the document.

  • Not exactly what I asked, but nice idea, thank you. – Cristi Stoica Aug 24 '13 at 20:20
  • @CristiStoica I added a new implementation – egreg Aug 24 '13 at 21:01
3

Here's a quick and dirty approach that could be made somewhat more automated:

\documentclass{article}
\usepackage{xparse}

\newtheorem{theorem}{Theorem}
\newtheorem{definition}[theorem]{Definition}

\ExplSyntaxOn

\NewDocumentEnvironment{mydef}{ o }
    {
        \bool_new:c {g_#1_bool}
        \bool_gset_true:c {g_#1_bool}
        \begin{definition}
    }
    {
        \end{definition}
    }

\NewDocumentCommand{\evennumber}{}{
    \bool_if:cTF {g_evennumber_bool}
        {even~number}
        {\msg_error:nn {Oops} {You~have~used~an~undefined~term.}}
    }

\ExplSyntaxOff

\begin{document}

Here {\evennumber} is undefined so will produce an error.

\begin{mydef}[evennumber]
An {\evennumber} is an integer that is divisible by $2$.
\end{mydef}

%Here {\evennumber} is defined and won't produce an error.

\end{document}

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.