gpt4 book ai didi

Python、PyTables - 利用内核内搜索

转载 作者:行者123 更新时间:2023-12-01 06:18:24 24 4
gpt4 key购买 nike

我有包含多个组的 HDF5 文件,其中每个组包含一个包含 >= 2500 万行的数据集。在模拟的每个时间步长,每个智能体都会输出他/她在该时间步长感知到的其他智能体。场景中有约 2000 个智能体和数千个时间步;输出的 O(n^2) 性质解释了行数的巨大。

我感兴趣的是计算按类别划分的独特目击事件的数量。例如,代理属于一方、红色、蓝色或绿色。我想制作一个二维表,其中第 i 行、第 j 列是类别 j 中至少有一个类别 i 中的代理感知到的代理数量。 (我在此代码示例中使用了 Sides,但我们也可以通过其他方式对代理进行分类,例如通过他们拥有的武器或他们携带的传感器。)

这是一个示例输出表;请注意,模拟不会输出蓝色/蓝色的感觉,因为它需要大量的空间,而且我们对它们不感兴趣。绿色相同)

      blue     green      red
blue 0 492 186
green 1075 0 186
red 451 498 26

列是

  1. 勾选 - 时间步
  2. sensingAgentId - 进行感知的代理 ID
  3. sensedAgentId - 正在检测的代理 ID
  4. detRange - 两个代理之间的范围(以米为单位)
  5. senseType - 枚举类型,表示完成的传感类型

这是我当前用于完成此操作的代码:

def createHeatmap():
h5file = openFile("someFile.h5")
run0 = h5file.root.run0.detections

# A dictionary of dictionaries, {'blue': {'blue':0, 'red':0, ...}
classHeat = emptyDict(sides)

# Interested in Per Category Unique Detections
seenClass = {}

# Initially each side has seen no one
for theSide in sides:
seenClass[theSide] = []

# In-kernel search filtering out many rows in file; in this instance 25,789,825 rows
# are filtered to 4,409,176
classifications = run0.where('senseType == 3')

# Iterate and filter
for row in classifications:
sensedId = row['sensedAgentId']
# side is a function that returns the string representation of the side of agent
# with that id.
sensedSide = side(sensedId)
sensingSide = side(row['sensingAgentId'])

# The side has already seen this agent before; ignore it
if sensedId in seenClass[sensingSide]:
continue
else:
classHeat[sensingSide][sensedSide] += 1
seenClass[sensingSide].append(sensedId)


return classHeat

注意:我有 Java 背景,所以如果这不是 Pythonic,我很抱歉。请指出这一点并提出改进此代码的方法,我很想更加精通 Python。

现在,这非常慢:执行此迭代和成员资格检查大约需要 50 秒,并且这是最严格的成员资格标准集(其他检测类型有更多的行需要迭代)。

我的问题是,是否可以将工作从 python 移到内核搜索查询中?如果是这样,怎么办?我是否缺少一些明显的加速?我需要能够为一组运行中的每次运行(〜30)以及多组标准(〜5)运行此函数,因此如果可以加快速度,那就太好了。

最后一点:我尝试使用 psyco,但这几乎没有什么区别。

最佳答案

如果你有 N=~2k 特工,我建议将所有目击事件放入大小为 NxN 的 numpy 数组中。这很容易适合内存(整数大约为 16 兆)。只要在目击发生的地方存储 1。

假设您有一个数组sightings。第一个坐标是 Sensing,第二个坐标是 Sensed。假设您还有一维索引数组,列出哪些代理位于哪一侧。您可以通过以下方式获取 A 方 B 方的目击次数:

sideAseesB = sightings[sideAindices, sideBindices]
sideAseesBcount = numpy.logical_or.reduce(sideAseesB, axis=0).sum()

您可能需要在第一步中使用 sightings.take(sideAindices, axis=0).take(sideBindices, axis=1),但我对此表示怀疑。

关于Python、PyTables - 利用内核内搜索,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1971870/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com