Cómo ocultar código en RMarkdown, con la opción de verlo


Estoy escribiendo un documento RMarkdown en el que me gustaría volver a ejecutar algunos trozos (5 a 9). No hay necesidad de mostrar estos trozos de nuevo, así que consideré usar

```{r echo=FALSE}

Para hacer invisibles los trozos de repetición, como se describe en otra pregunta stackoverflow. Esto está bien, y produce los resultados deseados (ajuste mejorado de la segunda iteración - ver esta solución implementada aquí ).

En un mundo ideal, sin embargo, el código sería expandible para que el usuario podría ver exactamente lo que está pasando si quieren con fines educativos y claridad (por ejemplo, ver enlace a la solución de Greasemonkey aquí) en lugar de oculto como en mi segundo ejemplo de rpubs. La solución puede verse algo como esto, pero con una caja circundante más corta para evitar la distracción:

for (i in 1:nrow(all.msim)){ # Loop creating aggregate values (to be repeated later)
  USd.agg[i,]   <- colSums(USd.cat * weights0[,i])
}

for (j in 1:nrow(all.msim)){
weights1[which(USd$age <= 30),j] <- all.msim[j,1] /USd.agg[j,1] 
weights1[which(USd$age >= 31 & USd$age <= 50),j] <- all.msim[j,2] /USd.agg[j,2] 
weights1[which(USd$age >= 51),j] <- all.msim[j,3] /USd.agg[j,3] ## 
}
# Aggregate the results for each zone
for (i in 1:nrow(all.msim)){
  USd.agg1[i,]   <- colSums(USd.cat * weights0[,i] * weights1[,i])
}
# Test results 
for (j in 1:nrow(all.msim)){
weights2[which(USd$sex == "m"),j] <- all.msim[j,4] /USd.agg1[j,4]  
weights2[which(USd$sex == "f"),j] <- all.msim[j,5] /USd.agg1[j,5] 
}

for (i in 1:nrow(all.msim)){
USd.agg2[i,]   <- colSums(USd.cat * weights0[,i] * weights1[,i] * weights2[,i])
}

for (j in 1:nrow(all.msim)){
weights3[which(USd$mode == "bicycle"),j] <- all.msim[j,6] /USd.agg2[j,6]  
weights3[which(USd$mode == "bus"),j] <- all.msim[j,7] /USd.agg2[j,7] 
weights3[which(USd$mode == "car.d"),j] <- all.msim[j,8] /USd.agg2[j,8]  
weights3[which(USd$mode == "car.p"),j] <- all.msim[j,9] /USd.agg2[j,9]
weights3[which(USd$mode == "walk"),j] <- all.msim[j,10] /USd.agg2[j,10]
}
weights4 <- weights0 * weights1 * weights2 * weights3
for (i in 1:nrow(all.msim)){
USd.agg3[i,]   <- colSums(USd.cat * weights4[,i])
}
# Test results 
plot(as.vector(as.matrix(all.msim)), as.vector(as.matrix(USd.agg3)),
     xlab = "Constraints", ylab = "Model output")
abline(a=0, b=1)
cor(as.vector(as.matrix(all.msim)), as.vector(as.matrix(USd.agg3)))
#rowSums(USd.agg3[,1:3]) # The total population modelled for each zone, constraint 1
#rowSums(USd.agg3[,4:5])
#rowSums(USd.agg3[,6:10])

Estoy contento con la solución echo=F, pero sería aún más feliz con un fragmento de código ampliable.

Editar: todos los ejemplos de RPubs excepto el primero han sido eliminados, para evite obstruir su excelente sistema de publicación con esencialmente el mismo documento.

Author: Community, 2013-01-02

2 answers

Esto se ha hecho mucho más fácil con el rmarkdown paquete, que no existía hace tres años. Básicamente solo tienes que activar "plegado de código": http://rmarkdown.rstudio.com/html_document_format.html#code_folding . Ya no tiene que escribir ningún JavaScript.

 29
Author: Yihui Xie,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-04-06 19:19:37

Si agrega una etiqueta html antes de su código, puede usar selectores CSS para hacer cosas inteligentes a los bits de la salida: markdown pasa fácilmente el HTML:

<style>
div.hidecode + pre {display: none}
</style>

<div class="hidecode"></div>
```{r}
summary(cars)
```

Aquí mi regla de estilo CSS coincide con la primera etiqueta <pre> después de <div class=hidecode> y la establece como invisible. Markdown escribe el fragmento R con dos etiquetas <pre>: una para la R y otra para la salida, y este CSS captura la primera.

Ahora que sabes cómo hacer coincidir el código y los bloques de salida en CSS, puedes hacer todo tipo de cosas inteligentes con ellos en Javascript. Puedes poner algo en la etiqueta <div class=hidecode> y añadir un evento de clic que alterne la visibilidad:

<style>
div.hidecode + pre {display: none}
</style>
<script>
doclick=function(e){
e.nextSibling.nextSibling.style.display="block";
}
</script>

<div class="hidecode" onclick="doclick(this);">[Show Code]</div>
```{r}
summary(cars)
```

El siguiente paso en complejidad es hacer que la acción cambie, pero entonces también podría usar jQuery y volverse realmente funky. O utilice este método simple. Vamos a hacerlo con un botón, pero también necesita un div para obtener sus ganchos en el bloque PRE comando R, y el recorrido se complica un poco:

<style>
div.hideme + pre {display: none}
</style>
<script>
doclick=function(e){
code = e.parentNode.nextSibling.nextSibling.nextSibling.nextSibling
if(code.style.display=="block"){
 code.style.display='none';
 e.textContent="Show Code"
}else{
 code.style.display="block";
 e.textContent="Hide Code"
}
}
</script>

<button class="hidecode" onclick="doclick(this);">Show Code</button>
<div class="hideme"></div>
```{r}
summary(cars)
```

(Nota: Pensé que podría envolver R trozos en <div> etiquetas:

<div class="dosomething">
```{r}
summary(cars) 
``` 
</div>

Pero eso falla - ¿alguien sabe por qué?)

 9
Author: Spacedman,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-01-02 21:16:46