2017-10-21 107 views
1

我有一個數據框字典,其中每個字典鍵對應於樣本名稱,數據框本身有一個「時間」列和一些測量列(溫度,濃度等)。時間列在樣本中不一致(不同樣本的開始和結束時間不同,儘管我認爲所有時間點在開始和結束之間都被測量/具有相同的dT)。使用xarray合併基於列的熊貓數據框

我想合併所有的數據到一個單一的xarray,其中一個軸是時間,另一個軸是測量類型,第三個軸是樣本名稱。由於並非所有時間都是針對所有樣本進行測量的,因此應將丟失的數據替換爲nan。

我幾乎沒有使用xarray的經驗,但做了一個簡單的合併(從xict的dict構造xarray)我無法弄清楚如何讓「時間」變成一個軸(而不是每個樣本都隨時間連接在一起作爲數據列之一)。

謝謝你的幫助!

編輯:

這裏是代碼我有僞數據

import pandas as pd 
import xarray as xr 

#make fake data 
dfs = {'sample1':pd.DataFrame([[1,0,0],[2,0,0],[3,0,0]],columns = ["Time","ColA","ColB"]), 
    'sample2':pd.DataFrame([[2,1,1],[3,1,1],[4,1,1]],columns = ["Time","ColA","ColB"])} 

#code I use for real data 
xrs = {k: xr.DataArray(v) for k, v in dfs.items()} 
merged = xr.Dataset(variables).to_array(dim="samples") 

print(merged) 

輸出是:

<xarray.DataArray (samples: 2, dim_0: 3, dim_1: 3)> 
array([[[1, 0, 0], 
     [2, 0, 0], 
     [3, 0, 0]], 

     [[2, 1, 1], 
     [3, 1, 1], 
     [4, 1, 1]]], dtype=int64) 
Coordinates: 
    * dim_0 (dim_0) int64 0 1 2 
    * dim_1 (dim_1) object 'Time' 'ColA' 'ColB' 
    * samples (samples) <U7 'sample1' 'sample2' 

希望的輸出:

<xarray.DataArray (samples: 2, Time: 4, dim_1: 2)> 
array([[[0, 0], 
    [0, 0], 
    [0, 0], 
    [nan, nan]], 

    [[nan, nan] 
    [1, 1], 
    [1, 1], 
    [1, 1]]], dtype=int64) 
Coordinates: 
    * Time  (Time) int64 1 2 3 4 
    * dim_1 (dim_1) object 'ColA' 'ColB' 
    * samples (samples) <U7 'sample1' 'sample2' 
+0

你知道,在這個忙碌的世界數據科學的人不要有耐心去通過無樣品一大解釋數據。更好地添加一個示例輸入數據框和預期輸出 – Dark

+0

好點,完成 – Ilya

回答

1

Xarray支持兩種基本格式FO [R converting from pandas:表示要轉換成xarray.DataArray,其中indexcolumns已經正確標註軸的二維矩陣

  1. DataFrames。
  2. DataFrame代表平坦的「整齊數據」,其中index中的MultiIndex等級對應於結果上的所需軸和columns對應於xarray.Dataset中的期望變量。

您的格式與前者最接近,所以我們試試。事實證明,所有你缺少的是.set_index('Time')一個電話,表明該列應該用於標記軸:

In [23]: da = xr.Dataset({k: v.set_index('Time') for k, v in dfs.items()}).to_array(dim='samples') 

In [24]: da 
Out[24]: 
<xarray.DataArray (samples: 2, Time: 4, dim_1: 2)> 
array([[[ 0., 0.], 
     [ 0., 0.], 
     [ 0., 0.], 
     [ nan, nan]], 

     [[ nan, nan], 
     [ 1., 1.], 
     [ 1., 1.], 
     [ 1., 1.]]]) 
Coordinates: 
    * Time  (Time) int64 1 2 3 4 
    * dim_1 (dim_1) object 'ColA' 'ColB' 
    * samples (samples) <U7 'sample1' 'sample2' 

第二種方法也是值得我們思考的,因爲讓你的數據整理也將使它更容易與DataFrame一起工作(例如,輕鬆地將數據繪製在Seaborn中)。

一旦你的xarray.DataArray,則可以使用to_series()轉換回大熊貓:

In [22]: da.to_series() 
Out[22]: 
samples Time dim_1 
sample1 1  ColA  0.0 
       ColB  0.0 
     2  ColA  0.0 
       ColB  0.0 
     3  ColA  0.0 
       ColB  0.0 
     4  ColA  NaN 
       ColB  NaN 
sample2 1  ColA  NaN 
       ColB  NaN 
     2  ColA  1.0 
       ColB  1.0 
     3  ColA  1.0 
       ColB  1.0 
     4  ColA  1.0 
       ColB  1.0 
dtype: float64 

或用DataFrames堅持,你可以使用pd.melt到「融化」的範圍內的數據爲長,整齊的形式,例如,

In [26]: melted = pd.melt(dfs['sample1'], id_vars=['Time'], var_name='Measurement') 

In [27]: melted 
Out[27]: 
    Time Measurement value 
0  1  ColA  0 
1  2  ColA  0 
2  3  ColA  0 
3  1  ColB  0 
4  2  ColB  0 
5  3  ColB  0 

然後從xarray轉換隻是設置一個多指標,並呼籲.to_xarray()的事情:

In [28]: melted.set_index(['Time', 'Measurement']).to_xarray() 
Out[28]: 
<xarray.Dataset> 
Dimensions:  (Measurement: 2, Time: 3) 
Coordinates: 
    * Time   (Time) int64 1 2 3 
    * Measurement (Measurement) object 'ColA' 'ColB' 
Data variables: 
    value  (Time, Measurement) int64 0 0 0 0 0 0