2015-12-21 14 views
5

いくつかのヌルを含む可変長の一連のリストがあります。一つの例は次のとおりです。pandas IndexError/TypeError NaN値との矛盾

In [108]: s0 = pd.Series([['a', 'b'],['c'],np.nan]) 
In [109]: s0 
Out[109]: 
0 [a, b] 
1  [c] 
2  NaN 
dtype: object 

なく、他のすべてのNaNsが含まれています

In [110]: s1 = pd.Series([np.nan,np.nan]) 
In [111]: s1 
Out[111]: 
0 NaN 
1 NaN 
dtype: float64 

私は単純明快である各リストの最後の項目、必要があります。

In [112]: s0.map(lambda x: x[-1] if isinstance(x,list) else x) 
Out[112]: 
0  b 
1  c 
2 NaN 
dtype: object 

しかし、この私になっながらのそのisinstanceなしで、NaNsのインデックスのチョークがそれほど異なっていることを発見したs0s1

In [113]: s0.map(lambda x: x[-1]) 
... 
TypeError: 'float' object is not subscriptable 

In [114]: s1.map(lamda x: x[-1]) 
... 
IndexError: invalid index to scalar variable. 

誰もが理由を説明することはできますか?これはバグですか?私はPandas 0.16.2とPython 3.4.3を使用しています。

+0

興味深い質問です。これは 'pd.Series'が動作する方法と関係しています。これは' list'でこれを複製しようとしているため、 'np.array'は' TypeError'だけで終わっています。 – DeepSpace

+0

リストではなくタプルを試しましたか?私の経験では、データフレーム内のタプルがはるかに優れています。私は再作成しようとしなかったので、これがあなたの問題に対処しているかわかりません –

答えて

1

これは、実際にはパンダの問題ではなく、NumPyの問題です。

mapは、列内の値を反復処理して、一度に1つずつlambda関数に渡します。下の列/ Series in PandasはNumPy配列の単なる(スライス)ので、pandasは関数の基になる配列から値を取得するために次のように定義しますhelper function。これは、各反復でmapによって呼び出される:

PANDAS_INLINE PyObject* 
get_value_1d(PyArrayObject* ap, Py_ssize_t i) { 
    char *item = (char *) PyArray_DATA(ap) + i * PyArray_STRIDE(ap, 0); 
    return PyArray_Scalar(item, PyArray_DESCR(ap), (PyObject*) ap); 
} 

キービットがコピーnumpyのアレイのセクションをスカラー値を返すためにnumpyのAPI関数である、PyArray_Scalarです。

機能を構成するコードが長すぎてここに投稿することはできませんが、here'sコードベースでどこを見つけるか。我々が知る必要があるのは、それが返すスカラーが、それが使用されている配列のdtypeと一致することだけです。

s0objectdtypeであり、s1float64dtypeです。これは、PyArray_Scalarが各シリーズに対して異なるタイプのスカラーを返すことを意味します。それぞれ実際ののPythonfloat対象とnumpyのスカラ浮動オブジェクト:あなたはlambda機能を使用してそれらにインデックスをしようとすると、

>>> type(s0[2]) 
float 
>>> type(s1[0]) 
numpy.float64 

NaN値は、二つの異なる種類の、したがって異なるエラーとして返されます。

+0

多くのありがとう、非常にクリア! – majr