意图:使用熊猫根据汉明权重过滤二进制数。在这里,我检查二进制文件中出现的1的数目,并将计数写入df。
到目前为止的努力:
import pandas as pd
def ones(num):
return bin(num).count('1')
num = list(range(1,8))
C = pd.Index(["num"])
df = pd.DataFrame(num, columns=C)
df['count'] = df.apply(lambda row : ones(row['num']), axis = 1)
print(df)
输出:
num count
0 1 1
1 2 1
2 3 2
3 4 1
4 5 2
5 6 2
6 7 3
Intended output:
1 2 3
0 1 3 7
1 2 5
2 4 6
帮助!
答案 0 :(得分:3)
您可以使用pivot_table
。尽管您需要将index
定义为分组的cumcount
列的count
,但是pivot_table
不能自己解决所有问题:)
(df.pivot_table(index=df.groupby('count').cumcount(),
columns='count',
values='num'))
count 1 2 3
0 1.0 3.0 7.0
1 2.0 5.0 NaN
2 4.0 6.0 NaN
您也有参数fill_value
,尽管我不建议您使用它,因为您会得到混合类型。现在看来NumPy
是一个不错的选择,您可以使用new_df.to_numpy()
轻松地从结果中获取一个数组。
此外,我们着眼于ones
中的逻辑,我们可以将其向量化(基于this answer):
m = df.num.to_numpy().itemsize
df['count'] = (df.num.to_numpy()[:,None] & (1 << np.arange(m)) > 0).view('i1').sum(1)
这是对两种方法性能的检验:
df_large = pd.DataFrame({'num':np.random.randint(0,10,(10_000))})
def vect(df):
m = df.num.to_numpy().itemsize
(df.num.to_numpy()[:,None] & (1 << np.arange(m)) > 0).view('i1').sum(1)
%timeit vect(df_large)
# 340 µs ± 5.6 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
%timeit df_large.apply(lambda row : ones(row['num']), axis = 1)
# 103 ms ± 2.32 ms per loop (mean ± std. dev. of 7 runs, 10 loops each)
答案 1 :(得分:1)
我建议使用其他输出:
var1 + var2
这会给你
num = input()
n = int(num)
if n%2 !=0:
print('Weird')
if n%2==0 and n in range(2,6):
print('Not Weird')
if n%2==0 and n in range(6,21):
print('Weird')
if n%2==0 and n>20:
print('Not Weird')
else:
pass
是相同的信息,但格式略有不同。在原始的透视格式下,行是没有意义的,并且列的数量不确定。我建议行数不确定的情况更为常见。我认为您会发现此操作更容易进行。
或者考虑仅创建字典,因为DataFrame在这里增加了很多开销,但毫无益处:
df.groupby("count").agg(list)
给你
num
count
1 [1, 2, 4]
2 [3, 5, 6]
3 [7]
答案 2 :(得分:0)
这是一种方法
df.groupby('count')['num'].agg(list).apply(pd.Series).T