如何将pd.series转换为np.array,而不是数组数组?如何替换nan值?

mwkjh3gx  于 2021-08-25  发布在  Java
关注(0)|答案(2)|浏览(324)

我很难将所选数据从pd.df转换为np.array。相反,我得到了一个数组。我现在想知道为什么我不能马上得到一个普通的数组。我知道 to_numpy() ,但它不会产生预期的结果。我也不能替换nan值。你能帮我弄明白发生了什么事吗?谢谢!祝您有个美好的一天。
我的小例子:

import pandas as pd
import numpy as np

# prepare the example

d={}
d['key1']=np.array([np.nan,2,np.nan,4])
d['key2']=np.array([5,6,7,8])                 
d['key3']=np.array([9,10,11,12])       
print(d)
print(type(d))

# create example df

df=pd.DataFrame(index=[0,1,2,3,4,5],columns=['A','B'])
df.at[0,'A'] = d
df.at[1,'A'] = d
df.at[2,'A'] = d
df.at[3,'A'] = d
df.at[4,'A'] = d
df.at[5,'A'] = d

df

# extract data from selected rows

res1=df.loc[[1,2,3],'A'].apply(lambda x: x.get('key2')).to_numpy()
print(res1)
print(res1.shape) #(3,)

# res1 is an object filled with arrays.

# Why would I not get back immediately an array (3,4), please?

# How can I get a np.array like this, please?

# res2=np.array([[5, 6, 7, 8],[5, 6, 7, 8],[5, 6, 7, 8]])

# res2.shape #(3,4)

# The solution I found:

res3=np.stack(res1,axis=0)
print(res3)
print(type(res3))
print(res3.shape)

# Is there something better that results immediately in a np.ndarray with (3,4)?

# How can I replace the nan values, please?

res4=df.loc[[1,2,3],'A'].apply(lambda x: x.get('key1')).to_numpy(na_value=0)
print(res4) #nan not 0

非常感谢。
编辑:我澄清了第二个问题。例如,我只想将nan替换为0。在实际示例中,并非key1的所有数组都包含nan。我需要保持每个数组中元素的数量相同。很抱歉有人明白为什么我的例子会给出期望的结果吗?非常感谢。

8ljdwjyq

8ljdwjyq1#

尝试:

res4=df.loc[[1,2,3],'A'].str['key1'].values

# instead of using apply() and lambda use .str['key name'] to get a value of particular key

res4=np.vstack(res4)

# it's similar to np.stack() at axis=0

# Finally:

res4=np.where(pd.isna(res4),0,res4)

产量 res4 :

array([[0., 2., 0., 4.],
       [0., 2., 0., 4.],
       [0., 2., 0., 4.]])

对你的问题的解释:
您得到的值是numpy的数组系列:

df.loc[[1,2,3],'A'].str['key1']

# output:

1    [nan, 2.0, nan, 4.0]
2    [nan, 2.0, nan, 4.0]
3    [nan, 2.0, nan, 4.0]
Name: A, dtype: object

您可以通过Map类型检查:

df.loc[[1,2,3],'A'].str['key1'].map(type)

# output:

1    <class 'numpy.ndarray'>
2    <class 'numpy.ndarray'>
3    <class 'numpy.ndarray'>
Name: A, dtype: object

# OR

# just by:

df.loc[[1,2,3],'A'].str['key1'].values

# output:

array([array([nan,  2., nan,  4.]), array([nan,  2., nan,  4.]),
       array([nan,  2., nan,  4.])], dtype=object)

您将获得数组的数组
注:该 na_value 参数在 to_numpy() 方法不起作用,因为序列中的值存储在容器中(本例中为np.array)
此外,如果发生以下情况,它将不起作用: list , tupleset 因为它们也是容器(或者可以说是数据结构)
如果值未存储在容器中,则 na_value=0 行得通
考虑下面的例子:

s=pd.Series([5,4,7,np.nan,np.nan])

# Let's say I have this Series

df=pd.DataFrame(data=[[5,4,np.nan,np.nan,6],[2,np.nan,5,np.nan,7]]).T

# And this dataframe

# So the values inside Series and Dataframe are not stored in a container(the datatype is float)

现在我可以很容易地使用 na_value 参数 to_numpy() 方法:

s.to_numpy(na_value=0)

# output of above code:

array([5., 4., 7., 0., 0.])
df.to_numpy(na_value=0)

# output of above code:

array([[5., 2.],
       [4., 0.],
       [0., 5.],
       [0., 0.],
       [6., 7.]])

更新:
正如我上面提到的 na_value 参数在 to_numpy() 方法不起作用,因为序列中的值存储在容器中(本例中为np.array)
您将从dict中获得一个值数组(数组是一个保存值的容器),其键为“key1”
考虑下面的例子:

d={}
d['key1']=np.array([np.nan,2,np.nan,4])
d['key2']=np.array([5,6,7,8])                 
d['key3']=np.array([9,10,11,12])       
d1={}
d1['key1']=np.nan
d1['key2']=np.array([5,6,7,8])                 
d1['key3']=np.array([9,10,11,12]) 
df=pd.DataFrame(index=[0,1,2,3],columns=['A','B'])
df.at[0,'A'] = d
df.at[1,'A'] = d
df.at[2,'A'] = d1
df.at[3,'A'] = d1

现在如果你使用 na_value 您将获得的参数:

df['A'].str['key1'].to_numpy(na_value=0)

# output:

array([array([nan,  2., nan,  4.]), array([nan,  2., nan,  4.]), 0, 0],
      dtype=object)
                                           ^nan are not filled because they are inside the container(np.array)                      
                                                                ^nan fill with 0

注:
如果该系列包含真实dict,则可以使用 str['keyname'] 在一系列中获取该键的值的符号,当然它比 apply() 和匿名函数

eulz3vhy

eulz3vhy2#

第一个问题

使命感 to_numpy() 然后 np.stack() 似乎是正确的答案,我想不出更好或更短的方法。

第二个问题

我假设您希望用零替换NaN,而不是删除值(并更改形状)。以下代码将执行此操作:

res4 = df.loc[[1,2,3],'A'].apply(lambda x: x.get('key1')).to_numpy()
res4 = np.stack(res4)
np.where(np.isnan(res4), 0, res4)
``` `np.isnan` 生成具有相同形状的布尔遮罩,以及 `np.where` 将0置于其为真的位置,否则它将保留该值 `res4` .

相关问题