R problemas con el llenado de un vector mediante un bucle

Estoy de iterar sobre un vector, para cada elemento miro algo en una tabla por rowname y copia de la devolución en un vector diferente. El siguiente código se utiliza para que

gs1 = function(p)
{
output <- character() #empty vector to which results will be forwarded

for (i in 1:length(p)) {
test <- p[i]
index <- which(rownames(conditions) == test)
toappend <- conditions[index,3] #working
output[i] <- toappend
print(paste(p[i],index,toappend,output[i]))
}   
return(output)
}

Todo lo que escupe es un vector con los números….mientras que todas las otras variables, parece contener la información correcta (como se comprueba por la función de impresión)
Tengo la sensación de que estoy haciendo algo mal, muy mal en el llenado de la salida de vector… yo también podría utilizar

output <- c(output,toappend)

Pero que me da exactamente lo mismo, lo malo y extraño de salida.

Toda la ayuda es muy apreciada!

Ejemplo de salida

> gs1 = function(p)
+ {
+ output <- character() #empty vector to which results will be pasted
+ 
+ for (i in 1:length(p)) {
+ test <- p[i]
+ index <- which(rownames(conditions) == test)
+ toappend <- conditions[index,3] #working
+ 
+ output <- c(output,toappend)
+ output[i] <- toappend
+ print(paste(p[i],index,toappend,output[i],sep=","))
+ }
+ return(output)
+ }
> ###########################
> test <- colnames(tri.data.1)
> gs1(test)
[1] "Row.names,,,NA"
[1] "GSM235482,1,Glc A,5"
[1] "GSM235484,2,Glc A,5"
[1] "GSM235485,3,Glc A,5"
[1] "GSM235487,4,Xyl A,21"
[1] "GSM235489,5,Xyl A,21"
[1] "GSM235491,6,Xyl A,21"
[1] "GSM297399,7,pH 2.5,12"
[1] "GSM297400,8,pH 2.5,12"
[1] "GSM297401,9,pH 2.5,12"
[1] "GSM297402,10,pH 4.5,13"
[1] "GSM297403,11,pH 4.5,13"
[1] "GSM297404,12,pH 4.5,13"
[1] "GSM297563,13,pH 6.0,14"
[1] "GSM297564,14,pH 6.0,14"
[1] "GSM297565,15,pH 6.0,14"
 [1] "5"  "5"  "5"  "5"  "21" "21" "21" "12" "12" "12" "13" "13" "13" "14" "14" "14"
  • Algunos datos de la muestra sería bienvenido. ¿Qué es condiciones? ¿Qué estás tratando de hacer?
  • nos muestran de qué manera se output mal? Lo que se recibe y lo que se puede esperar?
  • entonces es exactamente como Joris diagnosticados. Mira str(conditions) y tome nota de qué tipo de datos de la tercera entrada/variable. Será factor. R almacena internamente como números, pero se imprime con bonitas etiquetas. Usted está recibiendo los números internos no el nivel de forma. as.character() va a resolver que, o bien, cuando usted lee en los datos, mira argumento stringsAsFactors en ?read.table.
InformationsquelleAutor Timtico | 2010-12-16

2 Kommentare

  1. 6

    Muy probable que usted está usando un marco de datos y no una mesa, y la probabilidad de que la tercera columna no es un personaje vector sino un factor. Y no hay necesidad de escribir esa función, usted puede fácilmente obtener la quería por:

    conditions[X,3]

    con X es un carácter de vector de nombres de fila. por ejemplo :

    X <- data.frame(
      var1 = 1:10,
      var2 = 10:1,
      var3 = letters[1:10],
      row.names=LETTERS[1:10]
    )
    > test <- c("F","D","A")
    > X[test,3]
    [1] f d a
    Levels: a b c d e f g h i j

    Para meterse en los personajes:

    > as.character(X[test,3])
    [1] "f" "d" "a"
    • +1 para la simplificación! Que me di cuenta de como iba a agregar algo para hacerla menos críptico después de su comentario.
    • omg… resulta que puedo volver a escribir el bucle: condiciones[colnames(tri.de datos.1),3]
    • de hecho, y bienvenidos a el poder de la R. 🙂 Vectorización y los índices son realmente una bendición. Usted podría poner algún tiempo en la comprobación de los archivos de ayuda y notas de la introducción de R, para llegar a familiarizarse con ellas, nunca se arrepentirán.
    • Me vi obligada a R debido a la Bioconductor paquetes, pero no me arrepiento en absoluto. Sé que es un mal hábito de hacer bucles, pero estoy demasiado acostumbrado 🙂
    • Aunque todavía no puedo comprender por qué el bucle que no funcionó en mi caso. Considero que Joris respuesta como la más adecuada, debo permanecer lejos de el bucle cuando puedo.
    • como yo y Gavin dijo que ya, su 3d variable es un factor. El valor almacenado es un número que hay, pero cada número tiene una etiqueta. Ahora toappend todavía tiene la etiqueta, pero la etiqueta se pierde cuando se agrega el valor de un carácter vectorial. Por lo tanto, sólo el número de restos. si usted str(condiciones) verás que.

  2. 3

    [Joris comentarios sugieren yo era demasiado críptica, por lo que algunas explicaciones adicionales]:

    Efectivamente, si hacemos caso de la tramitación en el bucle, esto es lo que tiene:

    > p <- 1:10
    > gs1 <- function(p) {
    +     output <- character()
    +     for(i in seq_along(p))  {
    +         output[i] <- p[i] * 10
    +         print(output)
    +     }
    +     return(output)
    + }
    > foo <- gs1(p)
    [1] "10"
    [1] "10" "20"
    [1] "10" "20" "30"
    [1] "10" "20" "30" "40"
    [1] "10" "20" "30" "40" "50"
    [1] "10" "20" "30" "40" "50" "60"
    [1] "10" "20" "30" "40" "50" "60" "70"
    [1] "10" "20" "30" "40" "50" "60" "70" "80"
    [1] "10" "20" "30" "40" "50" "60" "70" "80" "90"
    [1] "10"  "20"  "30"  "40"  "50"  "60"  "70"  "80"  "90"  "100"
    > foo
    [1] "10"  "20"  "30"  "40"  "50"  "60"  "70"  "80"  "90"  "100"

    Así gs1 es devolver algo, y output se llena, mientras toappend es acharacter o puede ser coaccionado de caracteres para ir en output. Ahora, si toappend no es lo que usted cree, entonces, que es donde va a empezar a tener problemas.

    Veo dos problemas potenciales; i) toappend es en realidad un factor (que es algo Joris menciona también) y está recibiendo el equivalente numérico de la codificación interna de ese nivel. En cuyo caso

    ouput[i] <- as.character(toappend)

    debería ser suficiente, o ii) index es mayor que la longitud de 1 y son cada vez más elementos en el vector que usted espera y por lo tanto en la próxima iteración de que se sobrescriban.

    Estás seguro toappend es un carácter único vector de longitud 1? ¿Y que nos muestran el resultado incorrecto (edita tu Pregunta y añadir la salida de la función) y que nos diga por qué está mal!

    Por supuesto, todo esto puede ser simplificado a conditions[p, 3] y no hay necesidad de un bucle pero supongo que su función real es más complejo?


    Nota sobre la configuración de bucles

    Como para los bucles en general, se comete el error de no preallocating de almacenamiento. Usted no debe hacer las cosas de la manera que son. Observe cómo en cada iteración R es tener que crecer output por un elemento por iteración. Lo mismo sería cierto de su output <- c(output, toappend) idioma. Esto implica un montón de redundante copia del vector que los pantanos de bucles hacia abajo. En su lugar, asignar suficiente espacio de almacenamiento en la delantera y llenar output como lo están haciendo. E. g.:

    gs2 <- function(p) {
        output <- character(length = length(p))
        for(i in seq_along(p))  {
            output[i] <- p[i] * 10
            print(output)
        }
        return(output)
    }

    que produce la siguiente salida:

    > gs2(p)
     [1] "10" ""   ""   ""   ""   ""   ""   ""   ""   ""  
     [1] "10" "20" ""   ""   ""   ""   ""   ""   ""   ""  
     [1] "10" "20" "30" ""   ""   ""   ""   ""   ""   ""  
     [1] "10" "20" "30" "40" ""   ""   ""   ""   ""   ""  
     [1] "10" "20" "30" "40" "50" ""   ""   ""   ""   ""  
     [1] "10" "20" "30" "40" "50" "60" ""   ""   ""   ""  
     [1] "10" "20" "30" "40" "50" "60" "70" ""   ""   ""  
     [1] "10" "20" "30" "40" "50" "60" "70" "80" ""   ""  
     [1] "10" "20" "30" "40" "50" "60" "70" "80" "90" ""  
     [1] "10"  "20"  "30"  "40"  "50"  "60"  "70"  "80"  "90"  "100"
     [1] "10"  "20"  "30"  "40"  "50"  "60"  "70"  "80"  "90"  "100"

    La duplicación de la última línea es debido a la auto-impresión del objeto (output) devuelto de la función.

    • errr, no perdió de mí no. Su función no parece ni remotamente relacionado a la una de la OP. Su impresión de la declaración es para fines de depuración, supongo. Si ejecuta su código (cambio de las condiciones a X) en mi prueba de dataframe, consigue, de hecho, un vector con los números como OP describe.
    • Yo qué manera? Todo lo que el OP está haciendo está bien así que la única explicación es que toappend no es lo que él piensa que es. Lo que yo digo en el envío de línea de respuesta (después de que el ejemplo de trabajo). Toda la tarde de la materia que está tratando de mostrar a los OP que la expansión de salidas dentro de los bucles en cada iteración es una estupidez…
    • Usted no tiene idea de lo que conditions parece. toappend es claramente no lo que el OP piensa que es y me dicen que en mi respuesta. Quiero señalar que el lenguaje (para citar JD Largo) que están utilizando funciona siempre como toappend es un único carácter, como parece ser la intención.
    • dado el hecho de que el OP dice que toappend se ve bien (se imprime), parece que lo que él piensa que es. OP selecciona una rowname a partir de la entrada p, y hace que uno por uno. Así se obtiene una fila de índice, un valor único de la columna 3 con la que el índice de fila que va en toappend. Esa parte se me olvida en su función, supongo que junto con el *10 me confundía. Toappend se convierte en un número cuando se lo pone en la salida. Supongo que la única explicación es que se trata de un factor. Nada más sé de los cambios de caracteres a números.
    • para la iniciación de la longitud completa del vector.
    • De hecho, la impresión es puro para la depuración. Voy a publicar y ejemplo de la salida. BTW condiciones es un dataframe que contiene rownames que yo Uso para la búsqueda, y quiero que el valor en la columna tres devuelto
    • ver a mi de la solución a continuación. No hay necesidad de obtener una función, usted puede hacer eso en una línea.
    • Supongo que interpreta «escupe es un vector con los números» en un sentido diferente a lo que hizo. Usted hizo el salto que el OP no esperaba cualquier número de caracteres. Además, usted tiene derecho a señalar la simplificación en el uso directo de indización – I fue la adición de la misma cosa a mi respuesta antes de ver lo que había escrito.
    • entonces no hay ninguna necesidad de un bucle, solo índice por p directamente. Joris y yo, ambos muestran que en nuestras respuestas, Joris ligeramente delante de mí (todavía estoy bebiendo mi café de la mañana).
    • Sí.. he tenido la idea de que esto podría ser hecho directamente en alguna manera. Vengo de un Perl de fondo y el uso de bucles muy a menudo en el R…
    • así que sería mejor escribir la salida[length(p)]<-carácter()? por lo que asigna un vector con la longitud de p (inputvector de la función?)
    • No, output <- character(length = length(p)) sería la forma normal de hacer esto.
    • Mire de nuevo en su código, y el archivo de ayuda ?character. la función de caracteres(x) se convierte en un personaje vector de longitud x. De lo que se escribe, se producirá un error, ya que el objeto de salida todavía no existe, así que usted no puede acceder a los x-esima índice.
    • ok, ustedes fueron los de la derecha. Gracias por todos los (muy rápido) ayudar a los chicos. Esto hace mi vida más fácil 🙂

Kommentieren Sie den Artikel

Bitte geben Sie Ihren Kommentar ein!
Bitte geben Sie hier Ihren Namen ein

Pruebas en línea