2016-08-10 7 views
8

द्वारा एक ही संपत्ति के साथ एकाधिक नोड्स को बदलें, मान लें कि मेरे पास neo4j में नोड्स की संपत्ति "नाम" है। अब मैं यह लागू करना चाहता हूं कि एक ही नाम के साथ सभी नोड्स की पहचान करके दिए गए नाम के लिए अधिकतम एक नोड है। अधिक स्पष्ट:neo4j: एक नोड

  1. सभी मूल तीन नोड से सभी गुण इकट्ठा: तीन नोड्स जहां नाम "कुत्ता" है देखते हैं, तो मैं उन्हें नाम "कुत्ता" है, जो के साथ सिर्फ एक नोड द्वारा प्रतिस्थापित किया जा करना चाहते हैं।
  2. क्या सभी आर्क्स मूल तीन नोड्स से जुड़े हुए हैं।

इसके लिए पृष्ठभूमि निम्न है: मेरे ग्राफ में, अक्सर उसी नाम के कई नोड्स होते हैं जिन्हें "बराबर" माना जाना चाहिए (हालांकि कुछ के पास दूसरों की तुलना में समृद्ध संपत्ति जानकारी है)। WHERE खंड में a.name = b.name डालना बेहद धीमा है।

संपादित करें: मैं यह उल्लेख करना भूल गया कि मेरा नियो 4j वर्तमान में संस्करण 2.3.7 का है (मैं इसे अपडेट नहीं कर सकता)।

दूसरा संपादन: नोड्स के लिए लेबल और संभावित आर्क के लिए लेबल की एक ज्ञात सूची है। नोड्स का प्रकार ज्ञात है।

तीसरा संपादित करें: मैं जावा से "नोड पतन" प्रक्रिया को ऊपर कॉल करना चाहता हूं, इसलिए साइफर प्रश्नों और प्रक्रियात्मक कोड का मिश्रण भी एक उपयोगी समाधान होगा।

+0

इन नोड्स के लिए लेबल ज्ञात हैं?इन सभी नोड्स के लिए यह वही है? और इस नोड्स के लिए रिश्तों के प्रकार के बारे में क्या? –

+0

क्या होना चाहिए यदि नोड 1 (नाम = ए) और नोड 2 (नाम = ए) के पास अलग-अलग मानों के साथ समान संपत्ति हो? –

+0

@ के.ई. यह वास्तव में मेरे मामले में कोई फर्क नहीं पड़ता। कोई भी मूल्यों में से एक को छोड़ सकता है या किसी दिए गए "संपत्ति" के लिए "संपत्ति 2" परिभाषित कर सकता है। सबसे महत्वपूर्ण बात यह है कि सभी आर्कों को इकट्ठा करना है, यानी नए नोड में सभी आने वाली और जाने वाली चापों को प्रतिस्थापित नोड्स के समान लेबल के साथ होना चाहिए। मेरे अनुरोध का मुख्य कारण यह है कि मेरे पास बहुत सारे आर्क ए -> बी 1, बी 2 -> सी हैं, जहां बी 1 और बी 2 "वास्तव में" एक ही नोड हैं और संबंध ए -> बी -> सी वह है जिसे मैं चाहता हूं ढूँढ़ने के लिए। –

उत्तर

3

मैं निम्नलिखित स्कीमा के साथ एक testcase बना दिया है:

CREATE (n1:TestX {name:'A', val1:1}) 
CREATE (n2:TestX {name:'B', val2:2}) 
CREATE (n3:TestX {name:'B', val3:3}) 
CREATE (n4:TestX {name:'B', val4:4}) 
CREATE (n5:TestX {name:'C', val5:5}) 

MATCH (n6:TestX {name:'A', val1:1}) MATCH (m7:TestX {name:'B', val2:2}) CREATE (n6)-[:TEST]->(m7) 
MATCH (n8:TestX {name:'C', val5:5}) MATCH (m10:TestX {name:'B', val3:3}) CREATE (n8)<-[:TEST]-(m10) 

निम्नलिखित उत्पादन में क्या परिणाम:

enter image description here

कहाँ नोड्स बी वास्तव में एक ही नोड्स हैं ।

//copy all properties 
MATCH (n:TestX), (m:TestX) WHERE n.name = m.name AND ID(n)<ID(m) WITH n, m SET n += m; 

//copy all outgoing relations 
MATCH (n:TestX), (m:TestX)-[r:TEST]->(endnode) WHERE n.name = m.name AND ID(n)<ID(m) WITH n, collect(endnode) as endnodes 
FOREACH (x in endnodes | CREATE (n)-[:TEST]->(x)); 

//copy all incoming relations 
MATCH (n:TestX), (m:TestX)<-[r:TEST]-(endnode) WHERE n.name = m.name AND ID(n)<ID(m) WITH n, collect(endnode) as endnodes 
FOREACH (x in endnodes | CREATE (n)<-[:TEST]-(x)); 

//delete duplicates 
MATCH (n:TestX), (m:TestX) WHERE n.name = m.name AND ID(n)<ID(m) detach delete m; 

जिसके परिणामस्वरूप उत्पादन इस तरह दिखता है:

enter image description here

चिह्नित करने की विभिन्न रिश्तों के प्रकार पता करने के लिए है कि आप नहीं है और यहाँ मेरे समाधान है।

सभी गुणों को नोड्स से "निचले" आईडी के साथ नोड्स में "उच्च" आईडी के साथ कॉपी किया गया है।

4

मुझे लगता है कि आपको नोड्स के पर्याय के समान कुछ चाहिए।

1) सभी नोड्स के माध्यम से जाओ और एक नोड पर्याय बनाने के लिए:

MATCH (N) 
WITH N 
    MERGE (S:Synonym {name: N.name}) 
    MERGE (S)<-[:hasSynonym]-(N) 
RETURN count(S); 

2) केवल एक नोड के साथ पर्यायवाची शब्द निकालें:

MATCH (S:Synonym) 
WITH S 
MATCH (S)<-[:hasSynonym]-(N) 
WITH S, count(N) as count 
WITH S WHERE count = 1 
DETACH DELETE S; 

3) परिवहन गुण और शेष समानार्थी शब्दों के लिए रिश्तों (साथ apoc):

MATCH (S:Synonym) 
WITH S 
MATCH (S)<-[:hasSynonym]-(N) 
WITH [S] + collect(N) as nodesForMerge 
CALL apoc.refactor.mergeNodes(nodesForMerge); 

4)निकालें 210 लेबल:

MATCH (S:Synonym)<-[:hasSynonym]-(N) 
CALL apoc.create.removeLabels([S], ['Synonym']); 
+0

आपके विस्तृत उत्तर के लिए धन्यवाद। दुर्भाग्य से, jqassistant Neo4j 2.3.3 का उपयोग करता है और apoc 3.0.0 की आवश्यकता होती है। –

+0

@JFMeier कृपया इन सीमाओं को दिए गए मूल प्रश्न को सही करें। –