Created
October 11, 2012 18:27
-
-
Save kmaed/3874502 to your computer and use it in GitHub Desktop.
2012/09/17 の解答
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
\documentclass[a4paper]{article} | |
\begin{document} | |
\makeatletter | |
%% \length{<token list>} | |
% <token list> に含まれるトークンの数の * に展開される.完全展開可能. | |
\def\length#1{\len@begin#1{\len@end}} | |
%% \len@begin<token list>{ | |
% { までのトークン列を取ってきて \len@count に渡す. | |
% 残りは \len@ifend に. | |
\def\len@begin#1#{\len@count{#1\len@count@end}\len@ifend} | |
%% \len@ifend{<token list>} | |
% もし <token list> が \len@end なら終端なので終わり. | |
% そうでなければ2つの括弧分の ** を出して <token list> は \length に渡し, | |
% 残りを処理する. | |
\def\len@ifend#1{% | |
\ifx\len@end#1\empty | |
\else | |
**\length{#1}\expandafter\len@begin | |
\fi} | |
%% \len@count{<token list>} | |
% { が含まれない <token list> 中のトークンの数の * に展開される. | |
% <token list> が \len@count@end だったら終わり. | |
% そうでなければ * を1つ出して,<token list> の先頭のトークンを1つ取り除く. | |
\def\len@count#1{% | |
\ifx\len@count@end#1% | |
\expandafter\@gobble | |
\else | |
*\expandafter\len@count@gobble | |
\fi{#1}} | |
%% \len@count@gobble{<token list>} | |
% <token list> の先頭のトークンを1つ取り除く. | |
% まず,<token list> の先頭がスペースかどうかを判定する. | |
% 一旦 \len@count@eat で判定後に残されたトークン列を取り除き, | |
% その後分岐する. | |
\edef\len@count@gobble#1{% | |
\unexpanded{\expandafter\len@count@eat | |
\ifx}\space#1% | |
\unexpanded{\expandafter\len@count@rmsp | |
\else | |
\len@count@end\expandafter\len@count@rmtop | |
\fi}{#1}} | |
%% \len@count@eat<token list>\len@count@end | |
% <token list> を除去する. | |
\def\len@count@eat#1\len@count@end{} | |
%% \len@count@rmsp{<token list>} | |
% <token list> の先頭のスペースを取り除き,残りのトークンを数える. | |
\def\len@count@rmsp#1{\expandafter\len@count\expandafter{\len@rmsp#1}} | |
%% \len@count@rmtop{<token list>} | |
% <token list> の先頭の非スペーストークンを取り除き,残りのトークンを数える. | |
\def\len@count@rmtop#1{\expandafter\len@count\expandafter{\@gobble#1}} | |
%% \len@rmsp<space> | |
% スペース文字を1つ取り除く. | |
\expandafter\def\expandafter\len@rmsp\space{} | |
%% 終端のトークンと異世界の \makeatother. | |
\def\len@end{\len@end} | |
\def\len@count@end{\len@count@end} | |
\makeatother | |
\def\check{\ifx\result\checkstr OK\else NG\fi} | |
\edef\result{\length{ \a {b\cd ef{g} }\h }} | |
\def\checkstr{*************} | |
\check | |
\edef\result{\length{{ }{ {}} {}}} | |
\def\checkstr{***********} | |
\check | |
\escapechar=-1 | |
\edef\result{\length{\expandafter\expandafter\expandafter}} | |
\escapechar=`\\ | |
\def\checkstr{***} | |
\check | |
\edef\result{\expandafter\length\expandafter{\csname ?TeX\endcsname}} | |
\def\checkstr{*} | |
\check | |
\edef\result{\length{{>>+<+<-}}} | |
\def\checkstr{*********} | |
\check | |
\edef\next{\noexpand\length{a\space\space\space b}} | |
\edef\result{\next} | |
\def\checkstr{*****} | |
\check | |
\end{document} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
http://d.hatena.ne.jp/zrbabbler/20120917/1347856569