Solución:
Finalmente encontré una solución al problema de etiquetas múltiples que es menos complicado:
MATCH (a) WITH DISTINCT LABELS(a) AS temp, COUNT(a) AS tempCnt
UNWIND temp AS label
RETURN label, SUM(tempCnt) AS cnt
Con esta consulta cifrada podemos obtener diferentes etiquetas presentes en neo4j y su recuento.
MATCH (n) RETURN DISTINCT LABELS(n), COUNT(n)
Es sorprendentemente complejo obtener un recuento por etiqueta, ya que los nodos pueden tener varias etiquetas y labels (n)
devuelve una colección de cadenas que representan esas etiquetas. En un gráfico que consta de tres nodos y dos etiquetas, como {:A}
, {:B}
y {:A:B}
, labels (n)
devuelve tres colecciones de cadenas distintas. En lugar de contar dos nodos con :A
y dos nodos con :B
, el resultado sería uno para cada una de las tres combinaciones de etiquetas. Ver consola. Para agregar por etiqueta, no por colección de etiquetas, tendría que agrupar por los valores dentro de la colección, lo cual es engorroso.
Tengo una forma fea de hacerlo, tal vez alguien pueda sugerir una mejor: primero averigüe el número máximo de etiquetas que tiene cualquier nodo.
MATCH (n)
RETURN max(length(labels(n)))
Luego encadene tantas consultas con UNION
, contando los nodos por la etiqueta en la posición i
en la colección, donde i
comienza en 0 y aumenta hasta el máximo de 1. Si los nodos tienen como máximo 3 etiquetas,
MATCH (n)
RETURN labels (n)[0] as name, count (n) as cnt
UNION MATCH (n)
RETURN labels (n)[1] as name, count (n) as cnt
UNION MATCH (n)
RETURN labels (n)[2] as name, count (n) as cnt
Esto agrega los recuentos de etiquetas correctamente, pero devuelve un null
contar para cada caso en el que el índice esté fuera de los límites de la colección. Para el primer regreso (el [0]
index) esto significa nodos que no tienen una etiqueta. Para las otras líneas, el recuento nulo significa igualmente nodos con menos etiquetas que las solicitadas, pero esta información es irrelevante, por lo que puede ignorarse.
MATCH (n)
RETURN labels (n)[0] as name, count (n) as cnt
UNION MATCH (n)
WITH labels (n)[1] as name, count (n) as cnt
WHERE name IS NOT NULL
RETURN name, cnt
UNION MATCH (n)
WITH labels (n)[2] as name, count (n) as cnt
WHERE name IS NOT NULL
RETURN name, cnt
Estoy seguro de que esto podría hacerse con más gracia, pero eso es todo lo que he conseguido.