[英]What is the correct graph data structure to differentiate between nodes with the same name?
我正在學習圖形(它們看起來非常有用),並且想知道我是否可以就構建圖形的可能方法獲得一些建議。
簡單來說,讓我們說我每天都會得到采購訂單數據,有些日子與前一天相同,而其他日子則不同。 例如,昨天我訂購了鉛筆和橡皮擦,我創建了兩個節點來代表它們,然后今天我收到了橡皮擦和標記的訂單,依此類推。 在每一天之后,我的程序還會看到誰訂購了什么,如果Bob昨天訂購了一支鉛筆,然后今天訂購了一支橡皮,它就會產生一個有針對性的優勢。 我的邏輯是,我可以看到誰在每天購買了什么,我可以跟蹤Bob的購買行為(也許可以用它來推斷自己或其他用戶的模式)。
我的問題是,我正在使用networkx(python)並為昨天創建節點'pencil',然后為day2創建另一個節點'pencil',我無法區分它們。
我想(並且已經)將它命名為day2-pencil,然后掃描整個圖形並剝離'day2-'來跟蹤鉛筆訂單。 這對我來說似乎不對(更不用說處理器上昂貴了)。 我認為關鍵是如果我能以某種方式將每一天標記為自己的子圖,那么當我想要研究特定日期或幾天時,我不必掃描整個圖表。
隨着我的測試數據越來越大,它變得越來越混亂,所以我想知道最佳實踐是什么? 任何生成建議都會很棒(因為networkx看起來非常全面,所以他們可能有辦法做到這一點)。
提前致謝!
更新:仍然沒有運氣,但這可能有用:
import networkx as nx
G=nx.Graph()
G.add_node('pencil', day='1/1/12', colour='blue')
G.add_node('eraser', day='1/1/12', colour='rubberish colour. I know thats not a real colour')
G.add_node('pencil', day='1/2/12', colour='blue')
我輸入以下命令G.node
是:
{'pencil': {'colour': 'blue', 'day': '1/2/12'}, 'eraser': {'colour': 'rubberish colour. I know thats not a real colour', 'day': '1/1/12'}}
它明顯覆蓋了1/1/12的鉛筆與1/2/12一支,不知道我是否可以制造一個。
這主要取決於你的目標。 您想要分析的是圖表設計中的決定性因素。 但是,看一下你的結構,一般結構就是Customers
和Products
節點,它們是按Days
連接的(我不知道這對你有什么幫助,但實際上這是一個二分圖 )。
所以你的結構將是這樣的:
node(Person) --- edge(Day) ---> node(Product)
比方說,鮑勃在2012年1月1日買了一支鉛筆:
node(Bob) --- 1/1/12 ---> node(Pencil)
好的,現在Bob在1/2/12買了另一支鉛筆:
-- 1/1/12 --
/ \
node(Bob) > node(Pencil)
\ /
-- 1/2/12 --
等......
這實際上可以通過networkx
。 由於節點之間有多條邊,因此您必須在MultiGraph
Mor MultiDiGraph
之間進行選擇,具體取決於邊緣的MultiDiGraph
。
In : g = networkx.MultiDiGraph()
In : g.add_node("Bob")
In : g.add_node("Alice")
In : g.add_node("Pencil")
In : g.add_edge("Bob","Pencil",key="1/1/12")
In : g.add_edge("Bob","Pencil",key="1/2/12")
In : g.add_edge("Alice","Pencil",key="1/3/12")
In : g.add_edge("Alice","Pencil",key="1/2/12")
In : g.edges(keys=True)
Out:
[('Bob', 'Pencil', '1/2/12'),
('Bob', 'Pencil', '1/1/12'),
('Alice', 'Pencil', '1/3/12'),
('Alice', 'Pencil', '1/2/12')]
到目前為止,還不錯。 你實際上可以查詢“愛麗絲是否在1/1/12購買鉛筆?”之類的內容。
In : g.has_edge("Alice","Pencil","1/1/12")
Out: False
In : g.has_edge("Alice","Pencil","1/2/12")
Out: True
如果您想在特定日期訂購所有訂單,情況可能會變糟。 糟糕的是,我不是指代碼方面,而是計算方面。 代碼方面它很簡單:
In : [(from_node, to_node) for from_node, to_node, key in g.edges(keys=True) if key=="1/2/12"]
Out: [('Bob', 'Pencil'), ('Alice', 'Pencil')]
但是這會掃描網絡中的所有邊緣並過濾掉您想要的邊緣。 我不認為networkx
有更好的方法。
嘗試這個:
為每個節點提供唯一的整數ID。 然后,創建一個字典,節點,這樣:
nodes ['pencil'] = [1,4,...] < - 其中所有這些都對應於具有鉛筆屬性的節點。 將'鉛筆'替換為您感興趣的其他任何屬性。
只需確保當您使用'pencil'添加節點時,您將更新字典:
節點[ '鉛筆']。追加(new_node_id)。 同樣節點刪除。
圖表不是最佳方法。 像MySQL這樣的關系數據庫是存儲這些數據並執行諸如何時購買的數據的正確工具。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.