
일부 프로그래밍 편집기 및 IDE는 합법적인 변수 이름과 불법적인 변수 이름을 다양한 방식으로 강조합니다. 이러한 구문 검사 및 강조 표시가 쉽게 허용되기를 바라지 listings
만 적어도 지금은 그렇지 않습니다. 나의 장기적인 목표는 다음과 호환되는 솔루션을 구현하는 것입니다. listings
그러나 지금은 문제의 매우 단순화된 버전을 보고 있습니다.
문자와 공백 토큰으로만 구성된 토큰 스트림의 첫 번째 단어를 구문 분석하고 싶습니다. 이건 꼭 해야 해토큰별 토큰하지만 각 토큰에 대해 몇 가지 확인을 수행해야 하기 때문입니다. 이를 위해 스트림을 구문 분석하고 토큰을 만날 \Word
때까지 매크로 에 저장하는 재귀 매크로를 사용합니다. .
그 단계에서는 \Word
빨간색으로 인쇄하는 등 일정한 방식으로 가공합니다. 나는단어공백 토큰에 의해 중단되지 않는 일련의 문자 토큰으로.
문제: 스트림에서 토큰이 .
아닌 다음 공간 토큰이 발견될 때 재귀를 중지하기 위해 코드에서 무엇을 변경해야 하는지 알 수 없기 때문에 여기서는 토큰 만 사용합니다. .
제어 공간( \
) 을 대체하는 것은 .
트릭을 수행하지 않는 것 같습니다. 내 코드에서 무엇을 변경해야 합니까?
나는 구문 분석을 위해 낮은 수준의 TeX 명령을 사용하는 솔루션을 선호하지만 LaTeX2e 및 LaTeX3 대안도 관심이 있습니다.
편집하다: 골대를 옮기는 것 같다면 사과드립니다만, 이미 게시된 답변 중 일부가 무효화될 수 있는 "토큰별 토큰" 요구 사항을 추가하여 질문을 좀 더 명확하게 해야 했습니다.
\documentclass{article}
\usepackage{xcolor}
\def\ParseWordandPrint#1{%
\if #1.%
\textcolor{red}{\Word}\ %
\else
\edef\Word{\Word#1}
\expandafter\ParseWordandPrint
\fi%
}
\def\InitParseWordandPrint#1{%
\def\Word{}
\ParseWordandPrint#1%
}
\begin{document}
\InitParseWordandPrint Hello.World
\end{document}
답변1
편집된 질문에 따라 삭제를 취소합니다.
공백으로 구분된 인수를 사용하면 한 번에 단어를 파악하는 것이 더 쉽습니다.그 다음에해당 문자를 문자별로 반복합니다. (예를 들어 여기서는 문자인지 확인합니다. 마지막 예는 다음과 같습니다.
illegal character 0
illegal character 1
문자를 문자별로 반복하려면 사용해야 하는 \futurelet
(또는 동등하게 \@ifnextchar
) 텐트에서 멈추는 문자가 있지만 문자 간 커른과 합자를 깨뜨리지 않기가 어렵기 때문에 단어가 별로 좋지 않습니다. 그래서 단어를 먼저 잡는 것이 더 쉽습니다.
\documentclass{article}
\usepackage{xcolor}
\def\InitParseWordandPrint#1 {\check#1\relax\textcolor{red}{#1} }
\def\check#1{%
\ifx\relax#1%
\else
\ifcat a#1%
\else
\typeout{illegal character #1}%
\fi
\expandafter\check
\fi}
\begin{document}
\InitParseWordandPrint Hello World
\InitParseWordandPrint World
Hello World
\InitParseWordandPrint W0r1d
\end{document}
답변2
TeX는 \def
구분된 매개변수 텍스트를 제공합니다. 따라서 이 경우 공백을 구분 기호로 사용할 수 있습니다.
\documentclass{article}
\usepackage{xcolor}
\def\ParseWordandPrint#1{%
\if #1.%
\textcolor{red}{\Word}\ %
\else%
\edef\Word{\Word#1}%
\expandafter\ParseWordandPrint%
\fi%
}
\def\InitParseWordandPrint#1{%
\def\Word{}%
\ParseWordandPrint#1%
}
\def\highlightfirst#1 {\textcolor{red}{#1} }
\begin{document}
\InitParseWordandPrint Hello.World
\highlightfirst Hello World.
\end{document}
답변3
LaTeX3를 사용하면 정말 쉽습니다.
\documentclass{article}
\usepackage{xparse,xcolor}
\ExplSyntaxOn
\NewDocumentCommand{\printfirstwordincolor}{ O{red} m }
{
\jubobs_pfwr:nn { #1 } { #2 }
}
\seq_new:N \l_jubobs_words_seq
\tl_new:N \l_jubobs_first_word_tl
\cs_new_protected:Npn \jubobs_pfwr:nn #1 #2
{
% split the input at spaces
\seq_set_split:Nnn \l_jubobs_words_seq { ~ } { #2 }
% pop off the leftmost item
\seq_pop_left:NN \l_jubobs_words_seq \l_jubobs_first_word_tl
% print the first item in the chosen color
\textcolor{#1}{ \l_jubobs_first_word_tl } ~ %
% print the other items adding spaces between them
\seq_use:Nn \l_jubobs_words_seq { ~ }
}
\ExplSyntaxOff
\begin{document}
\printfirstwordincolor{Hello World}
\printfirstwordincolor[green]{Addio mondo crudele}
\end{document}
입력 토큰을 토큰별로 처리하려는 경우 저장된 항목에 대한 매핑을 수행할 수 있습니다. 모든 'd'를 대문자로 쓰고 싶다고 가정해 보겠습니다.
\documentclass{article}
\usepackage{xparse,xcolor}
\ExplSyntaxOn
\NewDocumentCommand{\printfirstwordincolor}{ O{red} m }
{
\jubobs_pfwc:nn { #1 } { #2 }
}
\seq_new:N \l_jubobs_words_seq
\tl_new:N \l_jubobs_first_word_tl
\bool_new:N \l_jubobs_first_item_bool
\cs_new_protected:Npn \jubobs_pfwc:nn #1 #2
{
\seq_set_split:Nnn \l_jubobs_words_seq { ~ } { #2 }
\seq_pop_left:NN \l_jubobs_words_seq \l_jubobs_first_word_tl
\textcolor{#1}{ \l_jubobs_first_word_tl } ~ %
\seq_use:Nn \l_jubobs_words_seq { ~ }
}
\NewDocumentCommand{\printfirstwordincolorandcapitalizeD} { O{red} m }
{
\jubobs_pfwcacd:nn { #1 } { #2 }
}
\cs_new_protected:Npn \jubobs_pfwcacd:nn #1 #2
{
\seq_set_split:Nnn \l_jubobs_words_seq { ~ } { #2 }
\leavevmode
\bool_set_true:N \l_jubobs_first_item_bool
\seq_map_inline:Nn \l_jubobs_words_seq
{
\bool_if:NT \l_jubobs_first_item_bool
{ \c_group_begin_token \color{#1} }
\tl_map_inline:nn { ##1 }
{
\peek_charcode_remove:NT d { D } ####1
}
\bool_if:NT \l_jubobs_first_item_bool
{ \c_group_end_token \bool_set_false:N \l_jubobs_first_item_bool }
\c_space_tl
}
\unskip
}
\ExplSyntaxOff
\begin{document}
\printfirstwordincolor{Hello World}
\printfirstwordincolorandcapitalizeD[blue]{Addio mondo crudele}
\end{document}