Cross-references

LaTeX reads a document once, from top to bottom. So when \ref{fig:leaf} appears on page 2 and the figure it names is on page 40, the number does not yet exist — and the whole cross-referencing machinery of LaTeX, \label and \ref, exists to solve that one problem: the reference comes before its target. The answer is disarmingly plain: write the numbers into an .aux file on the first run and read them back on the second. This page follows that idea through the two compilations, the bold ?? that shows up in between, the reason a \label placed before its \caption reports the wrong number, and the improvements cleveref and varioref bring.

\label and \ref: call it by name, never by number

Cross-referencing rests on two commands. \label{key} binds the name key to the value of the counter most recently incremented at that point and prints nothing at all. \ref{key} inserts just the number that name stands for. LaTeX does the counting, so you never type a digit. The key is any string you like, and because the label travels with the object, you can reorder figures or move a whole section into another chapter and every reference follows along. A document that says “Figure 3” in hand-typed prose collapses after one such move; this one does not.

latex
\section{Introduction}
\label{sec:intro}

\begin{equation}
  \label{eq:euler}
  e^{i\pi} + 1 = 0
\end{equation}

\begin{figure}
  \centering
  \includegraphics{leaf}
  \caption{Vein structure of a leaf}
  \label{fig:leaf}          % after \caption, always
\end{figure}

As shown in Section~\ref{sec:intro}, equation~\eqref{eq:euler}
and Figure~\ref{fig:leaf} agree on page~\pageref{fig:leaf}.

One point trips up nearly everyone: \ref returns the number alone. The words “Figure”, “equation”, “Section” do not come with it — you write them yourself, and you join them to the number with a non-breaking space ~ rather than an ordinary space. Written Figure \ref{fig:leaf}, a line can end after “Figure” and strand the “3” on the next line; written Figure~\ref{fig:leaf}, it cannot break there. That small manual chore of naming the type is exactly what \cref and \autoref, further down, take over for you.

Why you compile twice: the .aux file and the ??

Cross-references do not settle in one compilation. Every time LaTeX meets a \label it writes that number and page into an .aux file carrying the same base name as your document — and what \ref can read is only what the previous run put there. On the first pass, therefore, the target values exist nowhere: the output shows a bold ?? and the log carries two warnings. Both are worth recognising on sight, because both are what people type into a search box.

log
LaTeX Warning: Reference `fig:leaf' on page 1 undefined on input line 17.
LaTeX Warning: There were undefined references.
LaTeX Warning: Label(s) may have changed. Rerun to get cross-references right.

That ?? is not an accident but a specification written into the LaTeX kernel. In latex.ltx, the macro \@setref sets \reset@font\bfseries ?? when a label turns out to be undefined, and issues the “Reference … undefined” warning on the very next line. It is bold on purpose: bold does not blend into the surrounding type, so the hole is impossible to miss. Compile again and the values from .aux come back, turning ?? into real numbers. If the numbering shifts and a referenced value changes, the warning returns — so the correct procedure is to repeat until it disappears (two passes usually suffice). latexmk runs that loop for you, and Overleaf compiles several times behind the scenes, which is why ?? is a rare sight there.

The .aux file is plain text, so you can simply open it and read. Each label contributes one \newlabel line, and that line carries five fields: the number, the page, the heading text, the anchor name to link to, and one held in reserve. The third field is why \nameref can drop in the title itself; the fourth is why hyperref knows where a click should land. When a reference misbehaves and the cause is not obvious, the shortest route is to open .aux and look for that line. If the line is missing, the \label was never picked up; if the value looks wrong, the problem is where it sits — the subject of the next section.

mydoc.aux
% one line per label: {number}{page}{title}{anchor}{spare}
\newlabel{sec:intro}{{1}{1}{Introduction}{section.1}{}}
\newlabel{fig:leaf}{{2}{3}{Vein structure of a leaf}{figure.2}{}}

When \ref gives the wrong number: put \label after \caption

A figure reference that does not match the figure — the cause is, almost without exception, where the \label sits. A \label does not pick up the figure number because it happens to be inside a figure environment. It picks up the value of the counter incremented just before it, and the figure environment increments no counter at all. The command that steps the counter is \caption. So a \label written right after \begin{figure} captures not the figure number but whatever counter was last stepped — usually the number of the section or chapter you are currently in.

This is easier to believe after you run it. Put one figure inside the seventh section, attach a label both before and after the \caption, and compile with pdfLaTeX from TeX Live 2024: the .aux records 7 for the label written before — the section number — and 1 for the one written after, the figure number. Not a single warning is issued. Both are plausible numbers, so LaTeX has no way to judge that one is wrong. Precisely because it does not stop with an error, this mistake slips past review and reaches print.

latex
\section{A}\section{B}\section{C}
\section{D}\section{E}\section{F}\section{G}   % we are now in section 7

\begin{figure}
  \label{fig:before}      % WRONG: no counter stepped yet -> picks up 7
  \centering\rule{2cm}{1cm}
  \caption{A leaf}        % <- this is what steps the figure counter
  \label{fig:after}       % RIGHT: picks up 1
\end{figure}

% .aux after two runs:
%   \newlabel{fig:before}{{7}{1}{}{}{}}
%   \newlabel{fig:after}{{1}{1}{}{}{}}

The rule condenses to one line: put \label immediately after the command that produces the number. For figures and tables that means after \caption (inside its argument is also fine); for headings, right after \section and friends; for numbered equations, inside the equation environment; for list entries, after \item. In a figure carrying several captions, a single label means the number depends on which \caption you placed it after. And you can safely treat the only legitimate reason to write \label before a \caption as being that there is no \caption at all.

\pageref, and how to name your labels

When you want the page rather than the number, use \pageref{key}. It takes the same label and returns the number of the page on which that \label was set, so you can cite both together, as in Figure~\ref{fig:leaf} on page~\pageref{fig:leaf}. Structurally it is simply the second field of the \newlabel line coming back to you. It earns its keep in documents readers physically leaf through — long reports, bound theses — rather than in something read on a screen.

You may name a key however you like, but the common practice is to prefix it with the kind of thing it points at: sec:, fig:, tab:, eq:, ch:, lst:. Two things follow. First, naming by contentfig:leaf — means reordering figures never forces a rename, whereas a name like fig:3 becomes a lie the moment you insert a second figure. Second, seeing \ref{fig:...} tells you the target's kind immediately, which makes your own source mechanically readable when you later switch the document over to \cref.

PrefixWhat it points at
ch:Chapters (\chapter)
sec:Sections and subsections (\section, \subsection)
fig:Figures (after the \caption in figure)
tab:Tables (after the \caption in table)
eq:Numbered equations (inside equation and friends)
lst:Code listings (after the \caption from listings)

\eqref: equation numbers that arrive with their parentheses (amsmath)

Equation numbers are conventionally written in parentheses — “by equation (3)” — but plain \ref returns only 3. Load amsmath and \eqref{key} supplies the parentheses, returning (3). The real gain here is not the keystrokes but the type: the parentheses \eqref produces are always set upright, whatever font surrounds them, so inside a theorem environment where the body text is italic they stay vertical. Type (\ref{eq:euler}) by hand and those very parentheses lean over with the italics.

cleveref: \cref and \Cref handle the word, and the plural

cleveref lifts referencing a level. \cref{key} prepends the word for the target's kind (abbreviated by default — “fig. 1” — or “figure 1” with the noabbrev option), and \Cref{key} capitalises it so the reference can open a sentence. Its real strength is lists and ranges: pass labels comma-separated with no spaces — \cref{fig:a,fig:b,fig:c} — and it sorts and joins the numbers, pluralising the word as it goes, to give something like “figs. 1, 2 and 4”. Better still, a consecutive run folds into a range automatically, so those three come out as “figs. 1 to 3”. \crefrange{first}{last} is the command for getting that same contraction while naming only the two endpoints.

The word it prepends is redefined with \crefname{type}{singular}{plural} (\Crefname for the capitalised form). This is also how you localise it: for Japanese, give the same word for both numbers, as in \crefname{figure}{図}{図}. To capitalise everywhere in the document, load the package with the capitalise option. And where you want the number without any word at all — inside parentheses, in a table cell — \labelcref{key} gives you exactly what plain \ref would.

There is an absolute rule about load order: cleveref goes after hyperref, varioref and amsmath — it checks for all three. cleveref builds its commands by detecting what hyperref has defined, so the reverse simply cannot work. Happily this does not fail silently — the cleveref.sty shipped with TeX Live 2024 checks the order at \begin{document} and stops with the message below. The varioref combination is a different matter: the cleveref manual prescribes the order varioref → hyperref → cleveref and warns that getting it wrong can make cross-references point at something else entirely, with no warning in either the output or the log.

latex
\usepackage{varioref}
\usepackage{hyperref}
\usepackage{cleveref}   % always last of the three

% If cleveref is loaded before hyperref, TeX Live 2024 stops with:
%   ! Package cleveref Error: cleveref must be loaded after hyperref!.
%   Package load order is wrong: load cleveref *after* hyperref.

\cref{fig:a,fig:b,fig:c}       % figs. 1 to 3   (consecutive: compressed)
\cref{eq:euler,eq:max}         % eqs. (1) and (4)
\Cref{sec:intro} explains ...  % Section 1 explains ...
\labelcref{fig:a}              % 1   (number only, like \ref)

% with \usepackage[noabbrev]{cleveref} the same lines give
%   figures 1 to 3 / equations (1) and (4)

varioref: “on the next page” instead of a bare page number

In a bound document “Figure 3 on the next page” reads better than a mechanical “Figure 3 on page 12”, and “on the facing page” better still when the two sit on one spread. varioref's \vref{key} prints the same number as \ref and then looks at where the reference and its target fall relative to each other, adding the wording that fits. If they share a page it adds nothing at all. When only the page guidance is wanted, \vpageref{key} does that alone, and its two optional arguments set the wording for the same-page case and the lead-in for the different-page case.

That cleverness has a price. What \vref prints depends on the result of typesetting — which page things landed on — and the length of what it prints can itself move a page break, so the values may need an extra compilation to settle. A log that keeps repeating “Rerun to get cross-references right” is usually this. Loaded together with cleveref, \vref is reformatted in cleveref's style, so if you use both, keep the order (varioref → hyperref → cleveref) and settle the whole document on the \cref family; you will have less to reason about.

latex
\usepackage{varioref}

See~\vref{fig:leaf}.
%   same page : See figure 3.
%   next page : See figure 3 on the next page.
%   far away  : See figure 3 on page 12.

The data is summarised \vpageref[above][]{tab:data}.

If you cannot decide, the practical answer is to settle the whole document on cleveref. It handles the kind word, the plural, multiple references and ranges by itself, which makes the classic slip — writing Figure~\ref{tab:...} where the target is a table — structurally impossible. \ref and \pageref remain essential for understanding the machinery, \eqref still earns its place in mathematics and \vref in bound work. The table below summarises what each one prints.

CommandWhat it printsComes from
\label{key}Tags the counter just incremented; prints nothingLaTeX kernel
\ref{key}The number alone (e.g. 3)LaTeX kernel
\pageref{key}The page number where the label was setLaTeX kernel
\eqref{key}Equation number in upright parentheses (e.g. (3))amsmath
\autoref{key}Kind word + number, the whole thing a link (e.g. Figure 3)hyperref
\nameref{key}The target heading's title text itselfhyperref
\vref{key}Number + page guidance (“on the next page”, …)varioref
\cref{key}Kind word + number; handles lists, ranges and pluralscleveref
\Cref{key}\cref with a capital initial, for opening a sentencecleveref
\crefrange{a}{b}A consecutive range (e.g. figures 1 to 3)cleveref
\labelcref{key}The number alone — \cref without the kind wordcleveref