Exportar datos de Twitter a Gephi usando R
He compilado un conjunto de datos que consta de miles de tweets con R.
El conjunto de datos básicamente se ve así:
Data <- data.frame(
X = c(1,2),
text = c("Hello @User1 #hashtag1, hello @User2 and @User3, #hashtag2", "Hello @User2 #hashtag3, hello @User1 and @User3, #hashtag4"),
screenname = c("author1", "author2")
)
Ahora quiero exportar este conjunto de datos a un formato gráfico compatible con Gephi (verFormatos Gráficos Soportados - Gephi)
Siempre que un "autor" mencione a un @usuario en el texto, debe haber un enlace directo del autor al usuario. En el caso anterior, los resultados deberían ser así:
autor1 -> @ Usuario2
autor1 -> @ Usuario3
autor2 -> @ Usuario1
autor2 -> @ Usuario3
¿Cómo puedo manipular mi conjunto de datos y exportarlo a un formato de gráfico compatible con Gephi?
Si es posible, preferiría el formato GEXF o GraphML. Si eso no es posible, también puedo trabajar con csv o una hoja de cálculo.
Pensé en resolver este problema toda la noche e hice algunos pasos en la dirección correcta (al menos eso espero). Pero necesito tu ayuda.
Como se mencionó anteriormente, tengo básicamente el siguiente conjunto de datos:
Data <- data.frame(
X = c(1,2),
text = c("Hello @User1 #hashtag1, hello @User2 and @User3, #hashtag2", "Hello @User2 #hashtag3, hello @User1 and @User3, #hashtag4"),
screenname = c("author1", "author2")
)
Quiero exportarlo a un formato GEXF para usarlo en Gephi.
Hay un paquete r para exportar datos r a GEXF, llamado rgexf (verhttps://bitbucket.org/gvegayon/rgexf/wiki/Installation) Usar elwrite.gexf
función del paquete, necesito al menos dos cosas:
1) una matriz de todos los nodos en la red (en mi caso, autores, usuarios y hashtags)
2) una matriz de todos los bordes entre estos nodos (es decir, las conexiones entre autores y usuarios, así como los hashtags).
En mis datos de Twitter, los autores nunca se imprimen con "@", aunque también pueden ser "usuarios". Así que al principio tengo que agregar "@" a los autores, para evitar la duplicación de nodos.
data$screenname <- sub("^", "@", data$screenname )
Luego necesito una matriz, que consta de todos los nodos en mi red (es decir, autores, usuarios y hashtags). Según este ejemplo, el resultado debería verse así:
people <- data.frame(matrix(c(1:9, '@author1', '@author2', '@user1', '@user2', '@user3', '#hashtag1', '#hashtag2', '#hashtag3', '#hashtag4'),ncol=2))
Entonces necesito una matriz de todos los bordes entre estos nodos. Según este ejemplo, el resultado debería verse así:
relations <- data.frame(matrix(c(1,3,1,4,1,5,1,6,1,7,2,4,2,3,2,5,2,8,2,9), ncol=2, byrow=T))
Finalmente, solo tengo que poner estas dos cosas juntas:
write.gexf(people, relations)
para obtener el siguiente archivo:
<?xml version="1.0" encoding="UTF-8"?>
<gexf xmlns="http://www.gexf.net/1.2draft" xmlns:viz="http://www.gexf.net/1.1draft/viz" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.gexf.net/1.2draft http://www.gexf.net/1.2draft/gexf.xsd" version="1.2">
<meta lastmodifieddate="2015-02-04">
<creator>NodosChile</creator>
<description>A graph file writing in R using "rgexf"</description>
<keywords>gexf graph, NodosChile, R, rgexf</keywords>
</meta>
<graph mode="static" defaultedgetype="undirected">
<nodes>
<node id="1" label="@author1"/>
<node id="2" label="@author2"/>
<node id="3" label="@user1"/>
<node id="4" label="@user2"/>
<node id="5" label="@user3"/>
<node id="6" label="#hashtag1"/>
<node id="7" label="#hashtag2"/>
<node id="8" label="#hashtag3"/>
<node id="9" label="#hashtag4"/>
</nodes>
<edges>
<edge id="0" source="1" target="3" weight="1"/>
<edge id="1" source="1" target="4" weight="1"/>
<edge id="2" source="1" target="5" weight="1"/>
<edge id="3" source="1" target="6" weight="1"/>
<edge id="4" source="1" target="7" weight="1"/>
<edge id="5" source="2" target="4" weight="1"/>
<edge id="6" source="2" target="3" weight="1"/>
<edge id="7" source="2" target="5" weight="1"/>
<edge id="8" source="2" target="8" weight="1"/>
<edge id="9" source="2" target="9" weight="1"/>
</edges>
</graph>
</gexf>
Pero, ¿cómo puedo extraer automáticamente los nodos y las relaciones entre estos nodos (los bordes) del ejemplo anterior y escribirlos en dos matrices?
¿Nadie sabe cómo resolver mi problema?
Traté de averiguar cómo extraer los nodos de mi ejemplo (es decir, los autores, usuarios y hashtags) y guardarlos en un marco de datos (¡estoy seguro de que hay una forma más corta y elegante de hacerlo!):
#extract Users and Hashtags from text, Authors from screenname (and add @ to Author-names)
Users <- stri_extract_all(Data$text, regex = "@[A-Za-z0-9]+")
Hash <- stri_extract_all(Data$text, regex = "#[A-Za-z0-9]+")
Data$screenname <- sub("^", "@", Data$screenname )
Authors <- stri_extract_all(Data$screenname, regex = "@[A-Za-z0-9]+")
# delete NAs
Users <- Users[!is.na(Users)]
Hash <- Hash[!is.na(Hash)]
# converting lists to vectors
Users <- unlist(Users)
Hash <- unlist(Hash)
Authors <- unlist(Authors)
# merging the vectors to a single vector and deleting the duplicates
nodes <- unique(c(Authors, Users, Hash))
# saving the vectors in a data.frame and giving each node a unique ID
nodes <- data.frame(matrix(c(1:length(nodes), nodes), ncol=2))
colnames(nodes) <- c("ID", "label")
Pero, ¿cómo puedo construir un data.frame para los bordes?
Debe haber una manera de escribir una función que verifique automáticamente si un autor ha mencionado un usuario y / o un hashtag fila por fila y escribe el resultado en un nuevo data.frame, utilizando los ID de los autores, usuarios y hashtags. Cada conexión debe mostrarse en dos columnas: origen y destino (1,2).