`xifthen` 的 `isodd` 使用有什么问题?

`xifthen` 的 `isodd` 使用有什么问题?

可以通过测试节点位置的奇偶性来绘制白板/黑板,如下所示:

white-black-board

\documentclass[tikz]{standalone}
\usepackage{xifthen}

\begin{document}
\begin{tikzpicture}[every node/.style = {draw, circle, minimum size = 10pt}]
  \foreach \r in {1, ..., 4} {
    \foreach \c in {1, ..., 5} {
      \pgfmathparse{mod(\r + \c, 2)} 
      \let\parity\pgfmathresult 

      \ifthenelse{\equal{\parity}{0.0}}
      {\node (\r\c) [fill = lightgray] at (\c, \r){}}
      {\node (\r\c) at (\c, \r){}};
    }
  }
\end{tikzpicture}
\end{document}

但是,使用isoddofxifthen不会产生相同的结果。这里有什么问题?或者还有其他类似的解决方案吗?

white-black-board-wrong

\documentclass[tikz]{standalone}
\usepackage{xifthen}

\begin{document}
\begin{tikzpicture}[every node/.style = {draw, circle, minimum size = 10pt}]
  \foreach \r in {1, ..., 4} {
    \foreach \c in {1, ..., 5} {
      \ifthenelse{\NOT \isodd{\r + \c}}
      {\node (\r\c) [fill = lightgray] at (\c, \r){}}
      {\node (\r\c) at (\c, \r){}};
    }
  }
\end{tikzpicture}
\end{document}

答案1

您隐含地假设 isodd 会进行计算。但事实并非如此,它实际上只是从参数的开头开始,直到遇到不再是数字的东西。因此,您需要先进行加法,然后将结果提供给 isodd。或者使用 pgf 的工具:

\documentclass{article}
\usepackage{tikz}
\usepackage{xifthen}

\begin{document}
\ifthenelse{\isodd{124blub}}{odd}{even}

\ifthenelse{\isodd{123blub}}{odd}{even}

\ifthenelse{\isodd{2+3}}{odd}{even}

\ifthenelse{\isodd{3+2}}{odd}{even}

\bigskip
\begin{tikzpicture}[every node/.style = {draw, circle, minimum size = 10pt}]
  \foreach \r in {1, ..., 4} {
    \foreach \c in {1, ..., 5} {
      \pgfmathsetmacro\mycolor{isodd{\numexpr\r+\c}?"lightgray":"white"}
      \node (\r\c) [fill =\mycolor  ] at (\c, \r){};
    }
  }
\end{tikzpicture}
\end{document}

enter image description here

答案2

我建议使用 TeX \ifodd(或etoolbox(英文):xifthen可以考虑与朋友过时的

enter image description here

\documentclass{article}

\usepackage{xfp,tikz}

\begin{document}

\begin{tikzpicture}[every node/.style = {draw, circle, minimum size = 10pt}]
  \foreach \r in {1, ..., 4} {
    \foreach \c in {1, ..., 5} {
      \ifodd\inteval{\r+\c}
        \node (\r\c) [fill = lightgray] at (\c, \r) {};
      \else
        \node (\r\c) at (\c, \r) {};
      \fi
    }
  }
\end{tikzpicture}

\end{document}

我用xfp因为它很方便,并且提供了可扩展的\inteval计算int功能eval,可用于调节选项,例如\ifodd。您也可以不使用xfp

      \ifodd\numexpr\r+\c\relax
      %...

答案3

\isodd无法计算;你可以这样做

\expandafter\ifthenelse\expandafter{\expandafter\NOT\expandafter\isodd\expandafter{\the\numexpr\r+\c}}

但这不是我自己会用的东西。;-)

这里是允许表达式的(非插入式)重新实现xifthen;不过语法不同:对于括号,使用(and)而不是\(and \)。对于连接词,\AND\OR和分别被、和\NOT替换。&&||!

\documentclass{article}
\usepackage{tikz} % for the application

\ExplSyntaxOn
\NewExpandableDocumentCommand{\xifthenelse}{mmm}
 {
  \bool_if:nTF { #1 } { #2 } { #3 }
 }

\cs_new_eq:NN \numtest     \int_compare_p:n
\cs_new_eq:NN \oddtest     \int_if_odd_p:n
\cs_new_eq:NN \fptest      \fp_compare_p:n
\cs_new_eq:NN \dimtest     \dim_compare_p:n
\cs_new_eq:NN \deftest     \cs_if_exist_p:N
\cs_new_eq:NN \namedeftest \cs_if_exist_p:c
\cs_new_eq:NN \eqdeftest   \token_if_eq_meaning_p:NN
\cs_new_eq:NN \streqtest   \str_if_eq_p:ee
\cs_new_eq:NN \emptytest   \tl_if_empty_p:n
\cs_new_eq:NN \blanktest   \tl_if_blank_p:n
\cs_new_eq:NN \boolean     \legacy_if_p:n
\cs_new:Npn \modetest #1
 {
  \str_case:nnF { #1 }
   {
    {h}{\mode_if_horizontal_p:}
    {v}{\mode_if_vertical_p:}
    {m}{\mode_if_math_p:}
    {i}{\mode_if_inner_p:}
   }
   {\c_false_bool}
 }
\cs_new:Npn \enginetest #1
 {
  \str_case:nnF { #1 }
   {
    {luatex}{\sys_if_engine_luatex_p:}
    {pdftex}{\sys_if_engine_pdftex_p:}
    {ptex}{\sys_if_engine_ptex_p:}
    {uptex}{\sys_if_engine_uptex_p:}
    {xetex}{\sys_if_engine_xetex_p:}
   }
   {\c_false_bool}
 }

\ExplSyntaxOff

\begin{document}

1. \xifthenelse{\emptytest{}}{true}{false} true

2. \xifthenelse{\emptytest{ }}{true}{false} false

3. \xifthenelse{\emptytest{ foo }}{true}{false} false

4. \xifthenelse{\blanktest{}}{true}{false} true

5. \xifthenelse{\blanktest{ }}{true}{false} true

6. \xifthenelse{\numtest{10 * 10 + 1 > 100}}{true}{false} true

7. \xifthenelse{\numtest{10 * 10 + 1 > 100 * 100}}{true}{false} false

8. \xifthenelse{\eqdeftest{\usepackage}{\RequirePackage}}{true}{false} true

9. \xifthenelse{\eqdeftest{\usepackage}{\textit}}{true}{false} false

10. \xifthenelse{\namedeftest{@foo}}{true}{false} false

11. \xifthenelse{\namedeftest{@for}}{true}{false} true

12. \xifthenelse{\namedeftest{@for} || \numtest{1>2}}{true}{false} true

13. \xifthenelse{\namedeftest{@for} && \numtest{1>2}}{true}{false} false

14. \xifthenelse{\namedeftest{@for} && !\numtest{1>2}}{true}{false} true

15. \xifthenelse{!\oddtest{1+3}}{true}{false} true

16. \xifthenelse{\modetest{m}}{true}{false} false

17. $\xifthenelse{\modetest{m}}{true}{false}$ true

18. \parbox{2cm}{\xifthenelse{\modetest{v}}{true}{false}} true

19. \xifthenelse{\modetest{v}}{true}{false} false

20. \xifthenelse{\modetest{h}}{true}{false} true

21. \parbox{2cm}{\xifthenelse{\modetest{h}}{true}{false}} false

22. $\xifthenelse{\modetest{i}}{true}{false}$ true

23. \parbox{2cm}{\[\xifthenelse{\modetest{i}}{true}{false}\]} false

24. \xifthenelse{\fptest{22/7 = pi}}{true}{false} false

25. \xifthenelse{\enginetest{pdftex}}{true}{false} true

26. \xifthenelse{\enginetest{uptex}}{true}{false} false

\bigskip

\begin{tikzpicture}[every node/.style = {draw, circle, minimum size = 10pt}]
  \foreach \r in {1, ..., 4} {
    \foreach \c in {1, ..., 5} {
      \xifthenelse{!\oddtest{\r+\c}}
      {\node (\r\c) [fill = lightgray] at (\c, \r){}}
      {\node (\r\c) at (\c, \r){}};
    }
  }
\end{tikzpicture}

\end{document}

enter image description here

当然,对于图片情况使用PGF方法要容易得多。

相关内容