KD / Qtree实施

时间:2017-05-24 01:45:18

标签: python pandas dataframe cluster-computing quadtree

我有以下路径数据:

{{1}}

在上面的数据框中,(p1,p2)形成坐标数据和属于同一个" id1"的所有点。形成一条独立的道路;在上面的属于id1 = 1的df行(0-3)中是一条路径,依此类推。

我正在尝试实施四叉树来分析这些轨迹。为了实现四叉树,我试图使用" pyqtree" Android documentation python包。

在代码" len(spindex)"是边界框中的项目总数," bbox"格式为(xmin,ymin,xmax,ymax)," testitem"是交叉边界框,而len(匹配)将给出交集中的节点数。

我正在尝试使用上面的df来实现quadtree。请让我知道如何使用上面的df作为"项目"在代码中。然后如何为这些轨迹提供不同的边界框。此外,我如何知道或查询树以查找哪些轨迹位于四叉树的哪个区域。

2 个答案:

答案 0 :(得分:2)

因此,您需要查询每个轨迹的位置,这意味着您需要为每个轨迹计算并插入bbox。通常,这种类型的数据对于每个轨迹将具有一行,其中几何字段描述xy坐标的序列。但是由于你的坐标向下,我们必须先做一个解决方法,首先将属于每个轨迹id的所有xy点分组,然后计算bbox。

这是一个未经测试的示例代码,用于粉饰索引(我的大熊猫非常生疏,所以在那里有些错误):

for group in df.groupby('voygid'):
    bbox = [ group['x'].min(), group['y'].min(), group['x'].max(), group['y'].max() ]
    spindex.insert(group['voygid'][0], bbox)

不确定您打算如何进行群集,这将是一个单独的问题。四叉树的主要目的不是询问项目位于哪个四边形,而是询问哪些项目与任意任意bbox区域相交。

因此,如果将坐标区域划分为单独的聚类区域,则可以查询每个区域中的voygid轨迹。

for clusterbbox in clusters:
    voygids = spindex.intersects(clusterbbox)

请注意,项目可以跨越并位于多个四边形中,因此您可能需要或者可能不需要在之后进行额外的充实。

答案 1 :(得分:1)

要将轨迹转换为每个voygid的项目列表,我们可以使用pandas.groupby

<强>代码:

def get_items(group):
    return [Item(row[1].x, row[1].y) for row in group.iterrows()]

voygids = dict(df.groupby('voygid').apply(get_items))

如何吗

groupby将收集与特定voygid关联的行。然后我们可以使用pandas.DataFrame.apply()来调用一个函数,该函数将返回组中x, y对的项列表。该函数使用列表推导来构造Items()

列表

测试代码:

df = pd.read_fwf(StringIO(u"""
       voygid         x             y
        1             -7.935513     5.103579
        1             -7.935781     5.103300
        1             -7.936354     5.102726
        1             -7.935915     5.102802
        2             -7.935306     5.103424
        2             -7.945678     5.119876
        2             -7.954764     5.128738"""), header=1)
print(df)

class Item:
    def __init__(self, x, y):
      left = x-1
      right = x+1
      top = y-1
      bottom = y+1
      self.bbox = [left, top, right, bottom]

    def __repr__(self):
        return '[%s]' % ' '.join('%.4f' % x for x in self.bbox)

def get_items(group):
    return [Item(row[1].x, row[1].y) for row in group.iterrows()]

voygids = dict(df.groupby('voygid').apply(get_items))

for voygid, items in voygids.items():
    print(voygid)
    for item in items:
        print('  ' + repr(item))

<强>结果:

   voygid         x         y
0       1 -7.935513  5.103579
1       1 -7.935781  5.103300
2       1 -7.936354  5.102726
3       1 -7.935915  5.102802
4       2 -7.935306  5.103424
5       2 -7.945678  5.119876
6       2 -7.954764  5.128738

1
  [-8.9355 4.1036 -6.9355 6.1036]
  [-8.9358 4.1033 -6.9358 6.1033]
  [-8.9364 4.1027 -6.9364 6.1027]
  [-8.9359 4.1028 -6.9359 6.1028]
2
  [-8.9353 4.1034 -6.9353 6.1034]
  [-8.9457 4.1199 -6.9457 6.1199]
  [-8.9548 4.1287 -6.9548 6.1287]