有什么人会考虑使用Python合并两个数据集的最有效方法?
一点背景 - 此代码将采用以下格式的100K +记录:
{user: aUser, transaction: UsersTransactionNumber}, ...
并使用以下数据
{transaction: aTransactionNumber, activationNumber: assoiciatedActivationNumber}, ...
创建
{user: aUser, activationNumber: assoiciatedActivationNumber}, ...
N.B这些不是Python词典,只是最接近干净地描绘记录格式的东西。
所以从理论上讲,我所要做的就是创建一个连接共同密钥的两个列表(或表)的视图 - 首先这指向集合(工会等),但在我开始深入学习这些之前,他们是要走的路吗?到目前为止,我觉得这可以实现为:
创建一个字典列表并迭代列表,每次比较密钥,但最坏的情况是,这可能会运行到len(inputDict)* len(outputDict)< - 不确定?
将数据作为内存中的SQLite表进行操作?虽然对Python 2.4没有严格的要求,但它会让生活更轻松。
某种基于Set的魔法?
澄清
本脚本的总体目的是总结,实际数据集来自两个不同的来源。用户和交易号以CSV的形式出现,作为测试电子邮件激活码吞吐量的性能测试的输出。第二个数据集来自解析测试邮箱,其中包含事务ID和激活码。然后,此测试的输出将被转换回性能测试的第2阶段,使用已配对的激活码激活用户帐户。
如果我的记录符号具有误导性,我会道歉,我已相应地更新了它们。
感谢您的回复,我将尝试两个想法:
性能对我来说并不是最重要的,我只想尝试用Python编程养成良好的习惯。
答案 0 :(得分:6)
这是一种激进的方法。
别。
您有两个CSV文件;一个(用户)显然是驱动程序。别这一点。 另一个 - 用户的交易代码 - 可以变成一个简单的字典。
除非绝对必要,否则不要“合并”或“加入”任何东西。当然不要“合并”或“加入前”。
编写应用程序只需在其他集合中进行简单查找即可。
创建字典列表并迭代列表,每次比较密钥
关闭。看起来像这样。注意:没有排序。
import csv
with open('activations.csv','rb') as act_data:
rdr= csv.DictReader( act_data)
activations = dict( (row['user'],row) for row in rdr )
with open('users.csv','rb') as user_data:
rdr= csv.DictReader( user_data )
with open( 'users_2.csv','wb') as updated_data:
wtr= csv.DictWriter( updated_data, ['some','list','of','columns'])
for user in rdr:
user['some_field']= activations[user['user_id_column']]['some_field']
wtr.writerow( user )
这快速而简单。保存词典(使用shelve
或pickle
)。
然而,最糟糕的情况是这可能会运行到len(inputDict)* len(outputDict)< - 不确定?
假。
一个列表是“驾驶”列表。另一个是查找列表。您将通过迭代用户并查找适当的事务值来开车。这是用户列表中的 O ( n )。查找是 O (1),因为字典是哈希值。
答案 1 :(得分:1)
按交易号对两个数据集进行排序。这样,你总是只需要在内存中保留一行。
答案 2 :(得分:1)
这看起来像是以交易号为关键字典的字典。但是您不必创建公共结构,只需构建查找字典并根据需要使用它们。
答案 3 :(得分:0)
我创建了一个地图myTransactionNumber -> {transaction: myTransactionNumber, activationNumber: myActivationNumber}
,然后对{user: myUser, transaction: myTransactionNumber}
条目进行迭代,并在地图中搜索所需的myTransactionNumber
。搜索的复杂性应为O(log N)
,其中N
是集合中条目的数量。因此,总体复杂度为O(M*log N)
,其中M
是用户条目的数量。