迭代LaTeX中的字符/字符串数组

时间:2015-06-23 16:53:04

标签: arrays for-loop latex enumerate

这是我之前发布的问题的延续(Outputting character string elements neatly in Sweave in R)。我有一个字符串数组,我试图将每个元素输出到LaTeX。我可以使用以下代码实现这一点:

\documentclass[12pt,english,nohyper]{tufte-handout}
\usepackage[T1]{fontenc}
\usepackage[utf8]{inputenc}
\usepackage{longtable}
\usepackage{wrapfig}
\usepackaage{hyperref}
\usepackage{graphicx}
\usepackage[space]{grffile}
\usepackage{geometry}
\usepackage{enumitem}
\usepackage{pgffor}

\makeatletter
\makeatother

\begin{document}

<<include=FALSE>>=
library(ggplot2)
library(reshape2)
library(xtable)
@

\centerline{\Large\bf This is a test}
\vspace{1cm}

\noindent
My List:
\vspace{2mm}

<<echo=FALSE,results='asis'>>=
myList = c("A. This is the first item in my list.", "B. This is the second item in my list, and it will span across two lines because it is so long. This is the second item in my list, and it will span across two lines because it is so long.", "C. This is the third item in my list")
@

\begin{enumerate}[label=\Alph*., itemsep=-1ex]
  \item \Sexpr{str_trim(unlist(strsplit(chapter_outcomes[1], "[.]"))[2])}
  \item \Sexpr{str_trim(unlist(strsplit(chapter_outcomes[2], "[.]"))[2])}
  \item \Sexpr{str_trim(unlist(strsplit(chapter_outcomes[3], "[.]"))[2])}
\end{enumerate}

\end{document}

这为我提供了我希望实现的正确输出:

Correct formatting

但是,我现在正试图让这个迭代在for循环中发生,因为我在chapter_outcomes字符串数组中可能并不总是有三个元素。我尝试过以下变体:

\begin{enumerate}[label=\Alph*., itemsep=-1ex]
  \foreach \i in {\Sexpr{length(chapter_outcomes)}} {
  \item \Sexpr{str_trim(unlist(strsplit(chapter_outcomes[\i], "[.]"))[2])}
  }
\end{enumerate}

但是,这会导致chapter_outcomes [\ i]的上述语法出现“意外输入”错误。

我曾尝试查看类似的帖子(Iteration in LaTeXhttp://www.bytemining.com/2010/04/some-latex-gems-part-1-tikz-loops-and-more/),但他们的重点不同,我不能用它来解决我的问题。

感谢您的任何建议。

2 个答案:

答案 0 :(得分:1)

我没有使用Latex很长时间,但是:

1)不是\ foreach需要一个范围?如果我正确理解你的代码,\ Sexpr只评估长度(例如{6}),而\ foreach应该有{1..6}

2)另一个典型错误是运行{0 .. [length-1]}而不是{1 .. [length]}的索引,这可能导致“意外输入”,因为解释器试图移过最后一个元素

答案 1 :(得分:0)

听起来你应该看看expl3。我不使用R / Sweave,但是这里有一个例子可以帮助你。

\documentclass{article}
\usepackage{xparse,enumitem}

\ExplSyntaxOn

\cs_new_protected:Nn \lanner_sweave_wrap:n
  { \item \Sexpr { str_trim(unlist(strsplit(#1, "[.]"))[2]) } }

\cs_new_protected:Nn \lanner_sweave_enumlist:nn
  {
    \begin{enumerate}[#2]
      \seq_set_split:Nnn \l_tmpa_seq { ;;; } { #1 }
      \seq_map:NN \l_tmpa_seq \lanner_sweave_wrap:n
    \end{enumerate}
  }
\cs_generate_variant:Nn \lanner_sweave_enumlist:nn { f }

\NewDocumentCommand \EnumerateIt { O{label=\Alph*., itemsep=-1ex} m }
  { \lanner_sweave_enumlist:fn {#1} {#2} }

\ExplSyntaxOff

\begin{document}

<<echo=FALSE,results='asis'>>=
myList = c("A. This is the first item in my list.", "B. This is the second item in my list, and it will span across two lines because it is so long. This is the second item in my list, and it will span across two lines because it is so long.", "C. This is the third item in my list")
@

\EnumerateIt{\Sexpr{join(myList,";;;")}} % join myList with ";;;" -- I don't know the exact syntax

\end{document}

当然,这可以通过纯粹的explo3来完成:

\documentclass{article}
\usepackage{xparse,enumitem}

\ExplSyntaxOn

\tl_new:N \l_lanner_tmp_tl
\seq_new:N \l_lanner_tmp_seq
\cs_new_protected:Nn \lanner_sweave_enumlist:nn
  {
    \begin{enumerate}[#2]
      \tl_map_inline:nn {#1}
        {
          \seq_set_split:Nnn \l_lanner_tmp_seq { .~ } {##1}
          \seq_pop_left:NN \l_lanner_tmp_seq \l_lanner_tmp_tl

          \tl_set:Nf \l_lanner_tmp_tl
            { \seq_use:Nn \l_lanner_tmp_seq { .~ } }

          \tl_trim_spaces:N \l_lanner_tmp_tl

          \item \l_lanner_tmp_tl
        }
    \end{enumerate}
  }
\cs_generate_variant:Nn \lanner_sweave_enumlist:nn { f }

\NewDocumentCommand \EnumerateIt { O{label=\Alph*., itemsep=-1ex} >{ \SplitList { ;; } } m }
  {
    \tl_show:n{#2}
    \lanner_sweave_enumlist:fn {#2} {#1} }

\ExplSyntaxOff

\begin{document}

\EnumerateIt{
  A. This is the first item in my list. ;;
  B. This is the second item in my list, and it will span across two lines because it is so long,
     This is the second item in my list, and it will span across two lines because it is so long. ;;
  C. This is the third item in my list}

\end{document}