如何乘以Python中SArray中每个元素的每个值?
How to multiply to each value in each element in SArray in Python?
我正在使用 Graphlab,但我想这个问题可以应用于 pandas。
import graphlab
sf = graphlab.SFrame({'id': [1, 2, 3], 'user_score': [{"a":4, "b":3}, {"a":5, "b":7}, {"a":2, "b":3}], 'weight': [4, 5, 2]})
我想创建一个新列,其中 'user_score' 中每个元素的值乘以 'weight' 中的数字。也就是说,
sf = graphlab.SFrame({'id': [1, 2, 3], 'user_score': [{"a":4, "b":3}, {"a":5, "b":7}, {"a":2, "b":3}], 'weight': [4, 5, 2]}, 'new':[{"a":16, "b":12}, {"a":25, "b":35}, {"a":4, "b":6}])
我试着在下面写了一个简单的功能,但没有成功。有什么想法吗?
def trans(x, y):
d = dict()
for k, v in x.items():
d[k] = v*y
return d
sf.apply(trans(sf['user_score'], sf['weight']))
收到以下错误消息:
AttributeError: 'SArray' object has no attribute 'items'
我正在使用 pandas
数据框,但它也应该适用于您的情况。
import pandas as pd
df['new']=[dict((k,v*y) for k,v in x.items()) for x, y in zip(df['user_score'], df['weight'])]
输入数据帧:
df
Out[34]:
id user_score weight
0 1 {u'a': 4, u'b': 3} 4
1 2 {u'a': 5, u'b': 7} 5
2 3 {u'a': 2, u'b': 3} 2
输出:
df
Out[36]:
id user_score weight new
0 1 {u'a': 4, u'b': 3} 4 {u'a': 16, u'b': 12}
1 2 {u'a': 5, u'b': 7} 5 {u'a': 25, u'b': 35}
2 3 {u'a': 2, u'b': 3} 2 {u'a': 4, u'b': 6}
这是许多可能的解决方案之一:
In [69]: df
Out[69]:
id user_score weight
0 1 {'b': 3, 'a': 4} 4
1 2 {'b': 7, 'a': 5} 5
2 3 {'b': 3, 'a': 2} 2
In [70]: df['user_score'] = df['user_score'].apply(lambda x: pd.Series(x)).mul(df.weight, axis=0).to_dict('record')
In [71]: df
Out[71]:
id user_score weight
0 1 {'b': 12, 'a': 16} 4
1 2 {'b': 35, 'a': 25} 5
2 3 {'b': 6, 'a': 4} 2
这很微妙,但我想你想要的是:
sf.apply(lambda row: trans(row['user_score'], row['weight']))
apply 函数将一个函数作为参数,并将每一行作为参数传递给该函数。在您的版本中,您在调用 apply 之前评估 trans 函数,这就是为什么错误消息会抱怨在需要 dict 时将 SArray 传递给 trans 函数。
我正在使用 Graphlab,但我想这个问题可以应用于 pandas。
import graphlab
sf = graphlab.SFrame({'id': [1, 2, 3], 'user_score': [{"a":4, "b":3}, {"a":5, "b":7}, {"a":2, "b":3}], 'weight': [4, 5, 2]})
我想创建一个新列,其中 'user_score' 中每个元素的值乘以 'weight' 中的数字。也就是说,
sf = graphlab.SFrame({'id': [1, 2, 3], 'user_score': [{"a":4, "b":3}, {"a":5, "b":7}, {"a":2, "b":3}], 'weight': [4, 5, 2]}, 'new':[{"a":16, "b":12}, {"a":25, "b":35}, {"a":4, "b":6}])
我试着在下面写了一个简单的功能,但没有成功。有什么想法吗?
def trans(x, y):
d = dict()
for k, v in x.items():
d[k] = v*y
return d
sf.apply(trans(sf['user_score'], sf['weight']))
收到以下错误消息:
AttributeError: 'SArray' object has no attribute 'items'
我正在使用 pandas
数据框,但它也应该适用于您的情况。
import pandas as pd
df['new']=[dict((k,v*y) for k,v in x.items()) for x, y in zip(df['user_score'], df['weight'])]
输入数据帧:
df
Out[34]:
id user_score weight
0 1 {u'a': 4, u'b': 3} 4
1 2 {u'a': 5, u'b': 7} 5
2 3 {u'a': 2, u'b': 3} 2
输出:
df
Out[36]:
id user_score weight new
0 1 {u'a': 4, u'b': 3} 4 {u'a': 16, u'b': 12}
1 2 {u'a': 5, u'b': 7} 5 {u'a': 25, u'b': 35}
2 3 {u'a': 2, u'b': 3} 2 {u'a': 4, u'b': 6}
这是许多可能的解决方案之一:
In [69]: df
Out[69]:
id user_score weight
0 1 {'b': 3, 'a': 4} 4
1 2 {'b': 7, 'a': 5} 5
2 3 {'b': 3, 'a': 2} 2
In [70]: df['user_score'] = df['user_score'].apply(lambda x: pd.Series(x)).mul(df.weight, axis=0).to_dict('record')
In [71]: df
Out[71]:
id user_score weight
0 1 {'b': 12, 'a': 16} 4
1 2 {'b': 35, 'a': 25} 5
2 3 {'b': 6, 'a': 4} 2
这很微妙,但我想你想要的是:
sf.apply(lambda row: trans(row['user_score'], row['weight']))
apply 函数将一个函数作为参数,并将每一行作为参数传递给该函数。在您的版本中,您在调用 apply 之前评估 trans 函数,这就是为什么错误消息会抱怨在需要 dict 时将 SArray 传递给 trans 函数。