Introducción

Vectores y Subíndices

Un vector es una variable con uno o más valores del mismo tipo. Por ejemplo, tenemos el conjunto de números 4, 7, 6, 5, 6 y 7. El vector llamado peas es un objeto de length = 6. En este caso, la clase del objeto es numérica. La forma más sencilla de crear un vector en R es concatenar (enlazar) los seis valores utilizando la función de concatenación, c, así:

peas <- c(4,7,6,5,6,7)

Preguntas sobre vector peas

Podemos hacer todo tipo de preguntas sobre el vector peas. Por ejemplo, ¿qué tipo de vector es?

class(peas)
## [1] "numeric"

¿Qué tamaño tiene el vector?

length(peas)
## [1] 6

Ventaja de emplear vectores

La gran ventaja de un lenguaje basado en vectores es que es muy sencillo hacer preguntas bastante complicadas que implican todos los valores del vector. Estas funciones vectoriales suelen ser autoexplicativas:

mean(peas)
## [1] 5.833333
max(peas)
## [1] 7
min(peas)
## [1] 4

Otras pueden ser más elaboradas:

quantile(peas)
##   0%  25%  50%  75% 100% 
## 4.00 5.25 6.00 6.75 7.00

Otra forma de crear un vector

Otra forma de crear un vector es introducir los datos desde el teclado mediante la función scan:

peas <- scan()

En la consola aparece la pregunta 1: lo que significa que hay que escribir el primer número del vector (4) y luego pulsar la tecla Enter, luego aparece la pregunta 2: (se escribe 7) y así sucesivamente. Cuando haya introducido los seis valores y haya aparecido la pregunta 7:, sólo tiene que pulsar la tecla de Enter para indicar a R que el vector está completo. R responde diciéndole cuántos cuántos elementos ha leído

Para aplicaciones más realistas, la forma habitual de crear vectores es leer los datos de un archivo informático previamente preparado (descrito en el capítulo 3).

Extracción de elementos de un vector usando subíndices

A menudo querrá utilizar parte del contenido de un vector, pero no todo. Para ello, debe dominar el uso de los subíndices (o índices, como también se les conoce). En R, los subíndices implican el uso de corchetes[]. Nuestro vector peas:

peas <- c(4,7,6,5,6,7)

El primer elemento de peas es 4, el segundo 7, y así sucesivamente. Los elementos están indexados de izquierda a derecha, del 1 al 6. No puede ser más sencillo. Si queremos extraer el cuarto elemento de los valores (que puedes ver que es un 5) entonces esto es lo que hacemos:

peas[4]
## [1] 5

Si queremos extraer varios valores (digamos el 2do, el 3ro y el 6to) utilizamos un vector para especificar las datos que queremos como subíndices, ya sea en dos etapas como esta:

pods <- c(2,3,6)
peas[pods]
## [1] 7 6 7

O en un solo paso, así:

peas[c(2,3,6)]
## [1] 7 6 7

Puedes eliminar valores de un vector utilizando subíndices negativos. Aquí están todos los valores de peas:

peas[-1]
## [1] 7 6 5 6 7

Aquí están todos menos el último (nótese el uso de la función lenght para decidir cuál es el último):

peas[-length(peas)]
## [1] 4 7 6 5 6

Podemos utilizar estas ideas para escribir una función trim para eliminar (digamos) los dos valores más grandes y los dos más pequeños de un vector X. En primer lugar hay que usar el vectorsort, luego elimine los dos valores más pequeños (estos tendrán los subíndices 1 y 2), y luego elimine los dos valores más grandes (que tendrá subíndices length(x) y length(x)-1)

Por último, podemos utilizar secuencias de números para extraer valores de un vector. Aquí están los tres primeros valores de peas:

peas[1:3]
## [1] 4 7 6

Aquí están los valores pares de peas:

peas[seq(2,length(peas),2)]
## [1] 7 5 7

O alternativamente:

peas[1:length(peas) %% 2 == 0]
## [1] 7 5 7

Utilizando la función modulo %% en la secuencia 1 a 6 para extraer los números pares 2, 4 y 6. Tenga en cuenta que los vectores en R podrían tener longitud 0, y esto podría ser útil para escribir funciones:

y <- 4.3
z <- y[-1]
length(z)
## [1] 0

Clases de Vectores

El vector peas contenía números: en la jerga, es de la clase numeric. R permite vectores de seis tipos, siempre que todos los elementos de un vector pertenezcan a la misma clase. Las clases son lógicas, enteras, reales, complejas, cadenas (o caracteres) o brutas. Usted utilizará variables numéricas, lógicas y de carácter todo el tiempo. Los ingenieros y los matemáticos utilizarán números complejos. Pero podrías pasar toda una carrera sin tener que usar nunca números enteros o brutos.

Nombrar elementos dentro de vectores

A menudo es útil tener los valores de un vector etiquetados de alguna manera. Por ejemplo, si nuestros datos son recuentos de 0, 1, 2, . . . recurrimos al vector counts,

(counts <- c(25,12,7,4,6,2,1,0,2))
## [1] 25 12  7  4  6  2  1  0  2

Para que hubiera 25 ceros, 12 unos y así sucesivamente, sería útil nombrar cada una de los valores con el correspondiente número 0 a 8:

names(counts) <- 0:8

Ahora cuando inspeccionamos el vector counts vemos tanto los nombres como las frecuencias:

counts
##  0  1  2  3  4  5  6  7  8 
## 25 12  7  4  6  2  1  0  2

Si ha calculado una tabla de valores y desea eliminar los nombres, utilice la función as.vector así:

(st <- table(rpois(2000,2.3)))
## 
##   0   1   2   3   4   5   6   7   8   9  10 
## 197 466 517 392 236 135  29  20   6   1   1
as.vector(st)
##  [1] 197 466 517 392 236 135  29  20   6   1   1

Trabajar con subíndices lógicos

Tomemos el ejemplo de un vector que contiene los 11 números del 0 al 10:

x <- 0:10

Hay dos tipos de cosas bastante diferentes que podríamos querer hacer con esto. Podemos querer sumar los valores de los elementos:

sum(x)
## [1] 55

Otra posibilidad es contar los elementos que superan algún criterio lógico. Supongamos que queremos saber cuántos de los valores son menores de 5:

sum(x<5)
## [1] 5

Ya ves la distinción. Utilizamos la función vectorial sum en ambos casos. Pero sum(x) suma los valores de las xs y sum(x<5) cuenta el número de casos que pasan la condición lógica ‘x es menor que 5’. Esto funciona gracias a la coerción (p. 30). La condición lógica TRUE se ha convertido en un número 1 y la condición lógica FALSE se ha convertido en un número 0. Eso está muy bien, pero ¿cómo se suman los valores de sólo algunos de los elementos de x? Especificamos una condición lógica, pero no queremos contar el número de casos que pasan la condición, queremos sumar todos los valores de los casos que pasan. Esta es la última pieza del rompecabezas, e implica el uso de subíndices lógicos. Observe que cuando contamos el número de casos, el recuento se aplicó a todo el vector, utilizando sum(x<5). Para encontrar la suma de los valores de x que son menores que 5, escribimos:

sum(x[x<5])
## [1] 10

Veamos esto con más detalle. La condición lógica x<5 es verdadera o falsa:

x<5
##  [1]  TRUE  TRUE  TRUE  TRUE  TRUE FALSE FALSE FALSE FALSE FALSE FALSE

Se puede imaginar que falso es un 0 numérico y verdadero es un 1 numérico. Entonces el vector de subíndices [x<5] son cinco unos seguidos de seis ceros:

1*(x<5)
##  [1] 1 1 1 1 1 0 0 0 0 0 0

Ahora imagina que multiplicas los valores de x por los valores del vector lógico

x*(x<5)
##  [1] 0 1 2 3 4 0 0 0 0 0 0

Al aplicar la función sum, nos da la respuesta que queremos: la suma de los valores de los números 0 + 1 + 2 + 3 + 4 = 10.

sum(x*(x<5))
## [1] 10

Esto produce la misma respuesta que sum(x[x<5]), pero es mucho menos elegante. Supongamos que queremos calcular la suma de los tres valores más grandes de un vector. Hay dos pasos: primero se aplica sort para ordenar el vector en orden descendente; luego sumar los valores de los tres primeros elementos de la matriz ordenada de forma inversa. Hagamos esto por etapas. Primero, los valores de y:

y <- c(8,3,5,7,6,6,8,9,2,3,9,4,10,4,11)

Ahora bien, si se aplica sort a esto, los números estarán en secuencia ascendente, y esto complica un poco la vida para el presente problema:

sort(y)
##  [1]  2  3  3  4  4  5  6  6  7  8  8  9  9 10 11

Podemos utilizar la función inversa, rev de esta manera (utilice la tecla de flecha hacia arriba para ahorrar en la escritura):

rev(sort(y))
##  [1] 11 10  9  9  8  8  7  6  6  5  4  4  3  3  2

Así que la respuesta a nuestro problema es 11 + 10 + 9 = 30. Pero, ¿cómo se calcula esto? Un rango de subíndices es simplemente una serie generada con el operador dos puntos. Queremos los subíndices del 1 al 3, así que esto es:

rev(sort(y))[1:3]
## [1] 11 10  9

Así que la respuesta al ejercicio es solo:

sum(rev(sort(y))[1:3])
## [1] 30

Obsérvese que no hemos cambiado el vector y de ninguna manera, ni hemos creado ningún nuevo vector que consuma espacio durante los pasos intermedios del cálculo. A menudo querrás averiguar qué valor de un vector es el máximo o el mínimo. Esta es una pregunta sobre índices, y la respuesta que quieres es un entero que indique qué elemento del vector contiene el máximo (o el mínimo) de todos los valores de ese vector. Aquí está el vector:

x <- c(2,3,4,1,5,8,2,3,7,5,7)

Así que las respuestas que queremos son 6 (el máximo) y 4 (el mínimo). La forma lenta de hacerlo es así:

which(x == max(x))
## [1] 6
which(x == min(x))
## [1] 4

Sin embargo, es mejor utilizar las funciones incorporadas which.max o which.min, que son mucho más rápidas:

which.max(x)
## [1] 6
which.min(x)
## [1] 4