# \ifx doesn't treat \noexpand as \relax

The TeXbook (20th printing, Addison-Wesley 1991) describes how the primitive \noexpand<token> is expanded (p. 213):

The expansion is the token itself; but that token is interpreted as if its meaning were ‘\relax’ if it is a control sequence that would ordinarily be expanded by TeX’s expansion rules.

In light of this I expect the following plain TeX manuscript to typeset "yes". In fact, it typesets "no". Why?

\def\foo{bar}%
\expandafter\ifx\noexpand\foo\relax yes\else no\fi%
\bye

• @ShreevatsaR: Going by your logic, \expandafter\meaning\noexpand\foo is just like \meaning\foo and should therefore typeset "macro:->bar", but in fact it typesets "\relax". Aug 23, 2017 at 16:28
• I see, yes I probably don't understand everything here. Aug 23, 2017 at 16:29
• I suppose you could argue that \foo in this context is not a control sequence that would ordinarily be expanded by TeX’s expansion rules. For \ifx does not expand; it only checks whether two tokens mean the same. Unfortunately, this “explanation” does not explain the difference between \ifx and \meaning: The latter does not expand its argument either. I suppose it boils down to reading the TeX source code (which I never tried). Aug 23, 2017 at 17:01

You have to look first at module 358 of tex.web, where no_expand_flag is defined to be 257 (the comment says this characterizes a special variant of relax). When a macro is preceded by \noexpand, the variable cur_chr is assigned no_expand_flag and cur_cmd is assigned relax.
Module 507 explains how \ifx works: first the next token is stored, along with its cur_cmd and cur_chr values in p and q; thereafter, another token is absorbed and its cur_cmd is compared with p. In your case, this test returns true, because both values are relax.
The conclusion is that the expansion of \noexpand\foo is \relax, but not as far as \ifx is concerned and that this is by design.
• Thanks! What is cur_chr normally, for tokens that are not flagged as temporarily non-expandable? Aug 24, 2017 at 9:23
• @EvanAad “this characterizes a special variant of relax” seems to me clear enough a statement that this relax is not the same as one the user can input as \relax. The values assigned to cur_chr are clearly explained in tex.web. Aug 24, 2017 at 9:43