Gremlin ค้นหาเพื่อค้นหากราฟย่อยทั้งหมดที่มีการเชื่อมต่อโหนดเฉพาะในลักษณะใดก็ได้

Aug 19 2020

ฉันยังใหม่กับ Gremlin และกำลังใช้gremlin-pythonเพื่อสำรวจกราฟของฉัน กราฟประกอบด้วยคลัสเตอร์หรือกราฟย่อยจำนวนมากซึ่งเชื่อมต่อภายในและไม่เชื่อมต่อระหว่างกันกับคลัสเตอร์อื่นในกราฟ

ตัวอย่างง่ายๆคือกราฟที่มี 5 โหนดและ 3 ขอบ:

  • Customer_1เชื่อมต่อCreditCard_Aกับ1_HasCreditCard_Aขอบ
  • Customer_2เชื่อมต่อCreditCard_Bกับ2_HasCreditCard_Bขอบ
  • Customer_3เชื่อมต่อCreditCard_Aกับ3_HasCreditCard_Aขอบ

ฉันต้องการแบบสอบถามที่จะส่งคืนวัตถุกราฟย่อยของโหนดและขอบทั้งหมดที่เชื่อมต่อ (เข้าหรือออก) ไปยังโหนดที่สืบค้น จากนั้นฉันสามารถจัดเก็บกราฟย่อยนี้เป็นตัวแปรแล้วเรียกใช้การข้ามผ่านที่แตกต่างกันเพื่อคำนวณสิ่งต่างๆ

แบบสอบถามนี้จะต้องเรียกซ้ำเนื่องจากคลัสเตอร์เหล่านี้อาจประกอบด้วยโหนดซึ่งมีจำนวนมาก (ด้านในหรือด้านนอก) กระโดดออกจากกัน นอกจากนี้ยังมีโหนดและขอบหลายประเภทและจะต้องส่งคืนทั้งหมด

ตัวอย่างเช่น:

  • ถ้าผมระบุไว้Customer_1ในแบบสอบถามที่ส่งผลให้กราฟย่อยจะมีCustomer_1, Customer_3, CreditCardA, และ1_HasCreditCard_A3_HasCreditCard_A
  • ถ้าฉัน specififed Customer_2, กลับย่อยกราฟจะประกอบด้วยCustomer_2, ,CreditCard_B2_HasCreditCard_B
  • ถ้าฉันสอบถามCustomer_3อ็อบเจ็กต์ย่อยเดียวกันกับที่ส่งคืนจากCustomer_1คิวรีจะถูกส่งกลับ

ฉันใช้ทั้ง Neo4J กับ Cypher และ Dgraph กับ GraphQL แล้วและพบว่างานนี้ค่อนข้างง่ายในสองภาษานี้ แต่ฉันกำลังดิ้นรนอีกเล็กน้อยเพื่อทำความเข้าใจกับเกรมลิน

แก้ไข:

จากคำถามนี้คำตอบที่เลือกควรบรรลุสิ่งที่ฉันต้องการ แต่ไม่มีการระบุชนิดขอบโดยการเปลี่ยนเพียงแค่.both('created').both()

อย่างไรก็ตามไวยากรณ์ของลูป: .loop{true}{true}ไม่ถูกต้องใน Python แน่นอน ฟังก์ชันลูปนี้มีอยู่ในgremlin-pythonหรือไม่? ฉันไม่พบสิ่งใด

แก้ไข 2:

ฉันได้ลองสิ่งนี้แล้วและดูเหมือนว่าจะได้ผลตามที่คาดไว้ฉันคิดว่า

g.V(node_id).repeat(bothE().otherV().simplePath()).emit()

นี่เป็นวิธีแก้ปัญหาที่ถูกต้องสำหรับสิ่งที่ฉันกำลังมองหาหรือไม่? เป็นไปได้หรือไม่ที่จะรวมโหนดที่สืบค้นไว้ในผลลัพธ์นี้

คำตอบ

2 noam621 Aug 20 2020 at 13:51

สำหรับการแก้ไขครั้งที่สองสิ่งนี้ดูเหมือนวิธีแก้ปัญหาที่ถูกต้องซึ่งส่งคืนจุดยอดทั้งหมดที่เชื่อมต่อกับจุดยอดเริ่มต้น การแก้ไขเล็กน้อย:

  • คุณสามารถเปลี่ยนbothE().otherV()ไปboth()
  • หากคุณต้องการได้จุดยอดเริ่มต้นคุณต้องเลื่อนemitขั้นตอนก่อนหน้าไฟล์repeat
  • ฉันจะเพิ่มdedupขั้นตอนในการลบจุดยอดที่ซ้ำกันทั้งหมด (สามารถมากกว่า 1 พา ธ ไปยังจุดยอด)
g.V(node_id).emit().repeat(both().simplePath()).dedup()

exmaple: https://gremlify.com/jngpuy3dwg9