0

我正在学习图表(它们看起来非常有用)并且想知道是否可以就构建图表的可能方式获得一些建议。

简而言之,假设我每天都获得采购订单数据,有些日子与前一天相同,而在其他日子则不同。例如,昨天我订购了铅笔和橡皮擦,我创建了两个节点来表示它们,然后今天我收到了橡皮擦和马克笔的订单,依此类推。每天之后,我的程序还会查看谁订购了什么,如果 Bob 昨天订购了铅笔,然后今天订购了橡皮擦,它会创建一个有向边。我的逻辑是我可以看到谁每天买了什么,我可以跟踪 Bob 的购买行为(也许用它来推断他自己或其他用户的模式)。

我的问题是,我正在使用 networkx(python) 并为昨天创建一个节点“铅笔”,然后为第 2 天创建另一个节点“铅笔”,我无法区分它们。

我认为(并且一直)将其命名为 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/2/12 覆盖了 1/1/12 的铅笔,不确定我是否可以制作一个不同的铅笔。

4

3 回答 3

3

这实际上主要取决于您的目标。您要分析的是图形设计中的决定性因素。但是,查看您的结构,一般结构将是 和 的节点CustomersProducts它们通过以下方式连接Days(我不知道这是否会更好地帮助您,但这实际上是一个二分图)。

所以你的结构会是这样的:

node(Person) --- edge(Day) ---> node(Product)

假设 Bob 在 2012 年 1 月 1 日买了一支铅笔:

node(Bob) --- 1/1/12 ---> node(Pencil)

好的,现在 Bob 在 2012 年 1 月 2 日去买另一支铅笔:

          -- 1/1/12 --
         /            \
node(Bob)              > node(Pencil)
         \            /
          -- 1/2/12 --

很快...

这实际上是可能的networkx。由于节点之间有多个边,因此您必须根据边的定向性在MultiGraphMor之间进行选择。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')]

到目前为止,还不错。您实际上可以查询诸如“Alice 是否在 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没有更好的办法。

于 2012-01-12T04:46:46.857 回答
0

图表不是最好的方法。MySQL 等关系数据库是存储这些数据和执行诸如谁在何时购买什么的查询的正确工具。

于 2012-01-14T19:05:40.983 回答
0

试试这个:

给每个节点一个唯一的整数 ID。然后,创建一个字典、节点,这样:

nodes['pencil'] = [1,4,...] <- 其中所有这些都对应于具有铅笔属性的节点。用您感兴趣的任何其他属性替换“铅笔”。

只要确保当您使用“铅笔”添加节点时,您会更新字典:

节点['铅笔'].append(new_node_id)。节点删除也是如此。

于 2012-04-10T17:25:07.867 回答