6

I would like an automatic solution to referencing theorem environments containing lists using cleveref. In other words, if Corollary 1.2 contains parts (a) and (b), I want \cref to output “Corollary 1.2(a)” when referring to that theorem part. Horever, in proofs and similar situations, I want to be able to refer to, say, “part (a)” without having “1.2” in front.

Much of the solution is already available in this excellent answer, which contains the following example. However, as you see, I cannot write simply “(a)” without having the “1.2” part attached to it. How can this solution be modified to allow references to individual theorem parts without also getting the theorem number?

EDIT: I might add that I am actually going to use the ntheorem package to produce theorems, but I assume that it does not really change anything in the solution. And I think it is better to build upon the existing example.

enter image description here

\documentclass[english]{amsart}
\usepackage{babel}
\usepackage{enumitem}  % for '\newlist' and '\setlist' macros
\usepackage[colorlinks=true]{hyperref}
%%\usepackage{amsthm}  % is loaded automatically by amsart document class
\usepackage[nameinlink]{cleveref}

\newtheorem{thm}{Theorem}[section]
\crefname{thm}{Thm.}{Thms.} % singular and plural forms of label

\newtheorem{cor}[thm]{Corollary}
\crefname{cor}{Cor.}{Cors.} % singular and plural forms of label

\newlist{enumthm}{enumerate}{1} % set up a dedicated enumeration env.
\setlist[enumthm]{label=\upshape(\alph*),ref=\upshape\thethm(\alph*)}
\crefalias{enumthmi}{thm} % alias 'enumthmi' counter to 'thm'

\newlist{enumcor}{enumerate}{1} % set up a second dedicated enumeration env.
\setlist[enumcor]{label=\upshape(\alph*),ref=\upshape\thecor(\alph*)}
\crefalias{enumcori}{cor} % alias 'enumcori' counter to 'cor'


\begin{document}
\setcounter{section}{1} % just for this example

\begin{thm}\label{Thm:One}
The following properties hold:
\begin{enumthm}
    \item\label{Thm:One:1} \(1>0\)
    \item\label{Thm:One:2} \(0<1\)
\end{enumthm}
\end{thm}

\begin{cor}\label{Thm:Two}
The following properties hold as well:
\begin{enumcor}
    \item\label{Thm:Two:1} \(2>1\)
    \item\label{Thm:Two:2} \(1<2\)
\end{enumcor}
\begin{proof}
\ref{Thm:Two:1} follows from \ref{Thm:One:1} by adding 1 on both sides. Similarly, \cref{Thm:Two:2} follows from \cref{Thm:One:2}.
\end{proof}
\end{cor}

\end{document} 
  • 1
    Would you want the "label", i.e., "Corollary" or "Theorem", be part of the hypertarget generated by \cref? – Mico Oct 27 '16 at 11:57
  • @Mico You mean whether it should be a part of the clickable link in the hyperref reference? Preferably yes, but if one solution is much simpler and more beautiful than the other, it might be good to see both. – Gaussler Oct 27 '16 at 11:59
  • @Mico What I am saying is: It is not the most important part, the most important part is how it looks on paper. But yes, I like it to be all clickable, if that is not a great obstruction. – Gaussler Oct 27 '16 at 12:01
  • @Mico If necessary, I am also willing to use a separate reference command for this functionality, since I am mostly going to use it in special situations, like proofs. Something like \localref to output simply “(a)”. – Gaussler Oct 27 '16 at 12:11
  • you mention that you intend to use ntheorem to set your theorems. just a caution -- amsthm is incorporated directly into amsart; it's not a loaded package, so it can't easily be excluded. and there are some slight differences between the code in the class vs. the package, not in any way that materially affects the output, but it certainly isn't going to make using ntheorem at all easy, if you intend to continue using amsart. – barbara beeton Oct 30 '16 at 21:45
5
+100

cleveref stores the values of the enumi counter. You can extract them and then format them (I didn't try to add links, but this is possible to):

\documentclass[english]{amsart}
\usepackage{babel}
\usepackage{enumitem}  % for '\newlist' and '\setlist' macros
\usepackage[colorlinks=true]{hyperref}
%%\usepackage{amsthm}  % is loaded automatically by amsart document class
\usepackage[nameinlink]{cleveref}

\newtheorem{thm}{Theorem}[section]
\crefname{thm}{Thm.}{Thms.} % singular and plural forms of label

\newtheorem{cor}[thm]{Corollary}
\crefname{cor}{Cor.}{Cors.} % singular and plural forms of label

\newlist{enumthm}{enumerate}{1} % set up a dedicated enumeration env.
\setlist[enumthm]{label=\upshape(\alph*),ref=\upshape\thethm(\alph*)}
\crefalias{enumthmi}{thm} % alias 'enumthmi' counter to 'thm'

\newlist{enumcor}{enumerate}{1} % set up a second dedicated enumeration env.
\setlist[enumcor]{label=\upshape(\alph*),ref=\upshape\thecor(\alph*)}
\crefalias{enumcori}{cor} % alias 'enumcori' counter to 'cor'


\makeatletter
\newcounter{subcreftmpcnt} %
\newcommand\alphsubformat[1]{(\alph{#1})} %adapt ....
\newcommand\subcref[2][\alphsubformat]{%
\ifcsname r@#2@cref\endcsname
  \cref@getcounter {#2}{\mylabel}%
  \setcounter{subcreftmpcnt}{\mylabel}%
  \alphsubformat{subcreftmpcnt}%
 \else ?? \fi}   
\makeatother
\begin{document}
\setcounter{section}{1} % just for this example

\begin{thm}\label{Thm:One}
The following properties hold:
\begin{enumthm}
    \item\label{Thm:One:1} \(1>0\)
    \item\label{Thm:One:2} \(0<1\)
\end{enumthm}
\end{thm}



\begin{cor}\label{Thm:Two}
The following properties hold as well:
\begin{enumcor}
    \item\label{Thm:Two:1} \(2>1\)
    \item\label{Thm:Two:2} \(1<2\)
\end{enumcor}
\begin{proof}
\subcref{Thm:Two:1} follows from \ref{Thm:One:1} by adding 1 on both sides. Similarly,  \subcref{Thm:Two:2}  follows from \cref{Thm:One:2}.


\end{proof}
\end{cor}



\end{document} 

enter image description here

  • I experimented with this, and it looks very promising. I plan on giving you the bounty in a few days. But I feel it is my duty when I open a bounty to keep it open for some time in order to allow people to come with different possible solutions (even if I don’t see how one such could look like in this case). – Gaussler Oct 29 '16 at 17:43
  • well an alternative would be to use zref. It can store more than one representation from a label. – Ulrike Fischer Oct 29 '16 at 18:04
  • Agreed, as I also noted in a comment to the other answer. But since cleveref does not support zref, one would need to use two parallel label systems. Then it might make more sense to store the label in some kind of expl3 array. – Gaussler Oct 29 '16 at 18:07
  • One can redefine \label to issue the original label and zlabel. The main question is if it worth the time. – Ulrike Fischer Oct 29 '16 at 18:13
  • 1
    Is there any possibility that you include the code for adding links to the in-proof item references? Thank you anyway for your excellent answer! – Matemáticos Chibchas Apr 29 '18 at 5:53
3

I've interpreted your requirements and objectives as follows. First, the document has one or more important theorem-like environments (e.g., "Theorem") which may have multiple parts. When cross-referencing these parts individually, the cross-references should display the full (i.e., composite) number as well as the label "Theorem". Second, there are other, less important theorem-like environments (e.g., "Corollary") which may also have multiple parts. However, when cross-referencing parts of the less-important environments, only the sub-number (or letter) should be shown, not the full composite number. Moreover, the word "part" rather than "corollary" should be used as a label prefix.

If this understanding is correct, the following code should do what you're looking for. (If you don't want the label names to be part of the hypertargets, remove the option nameinlink while loading cleveref.)

enter image description here

\documentclass{article}
\usepackage{amsmath,amsthm}
\usepackage{enumitem}  % for '\newlist' and '\setlist' macros
\usepackage[colorlinks=true]{hyperref}
\usepackage[nameinlink]{cleveref}

\newtheorem{thm}{Theorem}[section]
\newtheorem{cor}[thm]{Corollary}

\newlist{enumthm}{enumerate}{1} % a dedicated enum. env.
   \setlist[enumthm]{label=\upshape(\alph*),
                     ref=\upshape\thethm(\alph*)}
\newlist{enumcor}{enumerate}{1} % another dedicated enum. env.
   \setlist[enumcor]{label=\upshape(\alph*)}

\crefname{thm}{Thm.}{Thms.}
\crefname{cor}{Cor.}{Cors.}
\crefname{enumthmi}{Thm.}{Thms.}
\crefname{enumcori}{part}{parts}

\begin{document}
\setcounter{section}{1} % just for this example

\begin{thm}\label{Thm:One}
The following properties hold:
\begin{enumthm}
    \item\label{Thm:One:a} $1>0$
    \item\label{Thm:One:b} $0<1$
\end{enumthm}
\end{thm}

\begin{cor}\label{Thm:Two}
The following properties hold as well:
\begin{enumcor}
    \item\label{Thm:Two:a} $2>1$
    \item\label{Thm:Two:b} $1<2$
\end{enumcor}
\begin{proof}
\Cref{Thm:Two:a} follows from \cref{Thm:One:a} by adding 1 on both sides. Similarly, \cref{Thm:Two:b} follows from \cref{Thm:One:b}.
\end{proof}
\end{cor}

\Cref{Thm:One:a,Thm:One:b} \dots;
\cref{Thm:Two:a,Thm:Two:b} of \cref{Thm:Two} \dots
\end{document}
  • I experimented with something similar, but it doesn’t work, unfortunately. The problem is that commands like \thecor are evaluated when \cref is executed, so it reads off the current value, which is the number of the last corollary. Try adding a new corollary after Thm:Two and refer to Thm:Two afterwards to see what i mean. – Gaussler Oct 27 '16 at 12:29
  • Notice also how it states that (a) follows from Theorem 1.2(a), whereas in the original example, it was Theorem 1.1(a). – Gaussler Oct 27 '16 at 12:43
  • @Gaussler - I've updated my answer; hopefully, it's now close(r) to what you're looking for. I suspect your stated objective -- use only the stub numbers (letters, actually) while in a proof environment but the full numbers elsewhere -- may not be achievable without some major hacking of the cleveref package. As Toby Cubitt, the author of the cleveref package, has written elsewhere, cleveref is clever but not omniscient. How is it supposed to know, all on its own, when to use stubs and when to use full numbers? – Mico Oct 28 '16 at 13:11
  • You might be right. I was perhaps thinking if the label itself (the value of label=) was stored somewhere, or if there was some way to extract the number of the label (here 1) and then modify it as “(a)” using \alph. I was playing around with the refcount package, but since the list is enumerated within the theorem counter, it does not seem possible to extract only the number 1, without the 1.2 part. – Gaussler Oct 28 '16 at 13:17
  • @Gaussler - Deep down, I guess, how is LaTeX to "know" that if (and only if, I suppose) it is in a proof-like environment, it has to strip off the prefixes from cross-references to "parts" if (and only if) these parts were generated in the immediately-preceding theorem-like environment, whereas the prefixes should not be stripped if the cross-reference is to an item in an earlier theorem-like env.? – Mico Oct 28 '16 at 13:23

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.