Trabajar con diccionarios / listas en R


Tengo una pregunta trivial: No pude encontrar una estructura de datos de diccionario en R, así que usé lista en su lugar (como "palabra" - > número) Por lo tanto, en este momento tengo problemas para obtener la lista de claves. Alguien sabe?

Author: smci, 2010-05-18

8 answers

Sí, el tipo list es una buena aproximación. Puede usar names() en su lista para establecer y recuperar las 'claves':

> foo <- vector(mode="list", length=3)
> names(foo) <- c("tic", "tac", "toe")
> foo[[1]] <- 12; foo[[2]] <- 22; foo[[3]] <- 33
> foo
$tic
[1] 12

$tac
[1] 22

$toe
[1] 33

> names(foo)
[1] "tic" "tac" "toe"
> 
 93
Author: Dirk Eddelbuettel,
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
2010-05-18 14:17:41

Ni siquiera necesita listas si sus valores de "número" son todos del mismo modo. Si tomo el ejemplo de Dirk Eddelbuettel:

> foo <- c(12, 22, 33)
> names(foo) <- c("tic", "tac", "toe")
> foo
tic tac toe
 12  22  33
> names(foo)
[1] "tic" "tac" "toe"

Las listas solo son necesarias si sus valores son de modo mixto (por ejemplo, caracteres y números) o vectores.

Tanto para listas como para vectores, un elemento individual puede ser subconjunto por nombre:

> foo["tac"]
tac 
 22 

O para una lista:

> foo[["tac"]]
[1] 22
 44
Author: Calimo,
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
2010-05-19 11:55:40

Para extender un poco la respuesta de Calimo, presento algunas cosas más que puede encontrar útiles al crear este cuasi dictionaris en R:

A) ¿cómo devolver todos los VALORES del diccionario:

>as.numeric(foo)
[1] 12 22 33

B) compruebe si el diccionario CONTIENE LA CLAVE:

>'tic' %in% names(foo)
[1] TRUE

C) cómo AGREGAR NUEVA clave, valor piar al diccionario:

C (foo,tic2=44)

Resultados:

tic       tac       toe     tic2
12        22        33        44 

D) cómo completar el requirment de DICCIONARIO REAL - que las claves NO PUEDEN repetir(CLAVES UNIQU)? Necesita combinar b) y c) y la función de compilación que valida si existe dicha clave, y hacer lo que desee: por ejemplo, no permita la inserción, actualice el valor si la nueva difiere de la antigua, o reconstruya de alguna manera la clave(por ejemplo, agrega algún número a ella para que sea única)

E) cómo ELIMINAR par POR CLAVE del diccionario:

Foo

 13
Author: Andrzej Kostański,
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-09-20 14:28:55

La razón para usar diccionarios en primer lugar es el rendimiento. Aunque es correcto que puede usar vectores con nombre y listas para la tarea, el problema es que se están volviendo bastante lentos y hambrientos de memoria con más datos.

Sin embargo, lo que mucha gente no sabe es que R tiene de hecho una estructura de datos de diccionario incorporada: entornos con la opción hash = TRUE

Vea el siguiente ejemplo para saber cómo hacerlo funcionar:

# vectorize assign, get and exists for convenience
assign_hash <- Vectorize(assign, vectorize.args = c("x", "value"))
get_hash <- Vectorize(get, vectorize.args = "x")
exists_hash <- Vectorize(exists, vectorize.args = "x")

# keys and values
key<- c("tic", "tac", "toe")
value <- c(1, 22, 333)

# initialize hash
hash = new.env(hash = TRUE, parent = emptyenv(), size = 100L)
# assign values to keys
assign_hash(key, value, hash)
## tic tac toe 
##   1  22 333
# get values for keys
get_hash(c("toe", "tic"), hash)
## toe tic 
## 333   1
# alternatively:
mget(c("toe", "tic"), hash)
## $toe
## [1] 333
## 
## $tic
## [1] 1
# show all keys
ls(hash)
## [1] "tac" "tic" "toe"
# show all keys with values
get_hash(ls(hash), hash)
## tac tic toe 
##  22   1 333
# remove key-value pairs
rm(list = c("toe", "tic"), envir = hash)
get_hash(ls(hash), hash)
## tac 
##  22
# check if keys are in hash
exists_hash(c("tac", "nothere"), hash)
##     tac nothere 
##    TRUE   FALSE
# for single keys this is also possible:
# show value for single key
hash[["tac"]]
## [1] 22
# create new key-value pair
hash[["test"]] <- 1234
get_hash(ls(hash), hash)
##  tac test 
##   22 1234
# update single value
hash[["test"]] <- 54321
get_hash(ls(hash), hash)
##   tac  test 
##    22 54321
 11
Author: vonjd,
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-02-20 18:24:55

Es posible que desee mirar el hash paquete en CRAN.

 5
Author: Jyotirmoy Bhattacharya,
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
2010-05-19 05:39:37

El paquete hash ya está disponible: https://cran.r-project.org/web/packages/hash/hash.pdf

Ejemplos

h <- hash( keys=letters, values=1:26 )
h <- hash( letters, 1:26 )
h$a
# [1] 1
h$foo <- "bar"
h[ "foo" ]
# <hash> containing 1 key-value pair(s).
#   foo : bar
h[[ "foo" ]]
# [1] "bar"
 5
Author: Ngọc Linh Vũ,
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-03-11 18:17:26

Solo voy a comentar que puede obtener un montón de kilometraje de table cuando se trata de" falso " un diccionario también, por ejemplo,

> x <- c("a","a","b","b","b","c")
> (t <- table(x))
x
a b c 
2 3 1 
> names(t)
[1] "a" "b" "c"
> o <- order(as.numeric(t))
> names(t[o])
[1] "c" "a" "b"

Etc.

 4
Author: Gabriel Perdue,
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
2015-05-21 15:45:18

Variación más corta de la respuesta de Dirk:

# Create a Color Palette Dictionary 
> color <- c('navy.blue', 'gold', 'dark.gray')
> hex <- c('#336A91', '#F3C117', '#7F7F7F')

> # Create List
> color_palette <- as.list(hex)
> # Name List Items
> names(color_palette) <- color
> 
> color_palette
$navy.blue
[1] "#336A91"

$gold
[1] "#F3C117"

$dark.gray
[1] "#7F7F7F"
 4
Author: Nettle,
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
2016-04-17 19:37:59