2015-10-20 29 views
5

Tôi có một dataframe trông như thế này:nếu báo cáo cho dataframes gấu trúc bằng Python

timestamp      0   1   2   3           
2013-04-17 05:00:00  4.335212 2655.140854 2655.140854 2655.140854 
2013-04-17 05:10:00  2.224966 2655.140854 2655.140854 2655.140854 
2013-04-17 05:20:00  2.409150 2655.140854 2655.140854 2655.140854 
2013-04-17 05:30:00 2655.140854 2655.140854 2655.140854 2655.140854 

tôi cần phải áp đặt một if tiêu chí tuyên bố trên tất cả các giá trị trong dataframe, tôi đã cố gắng sử dụng:

dirt = dirt.astype(float) 
for ind, i in enumerate(dirt): 
    if i < 0: 
     dirt[ind] = i + 360 
    if i > 360: 
     dirt[ind] = i - 360 

Tuy nhiên việc cộng và trừ không xảy ra trên bất kỳ giá trị nào. Bất kỳ ý tưởng?

Trả lời

3

Bạn nên sử dụng .iterrows() thay vì enumerate(df). Khi bạn làm enumerate(df), bạn chỉ cần lấy tên cột, tên này sẽ không đáp ứng được điều kiện của bạn. iterrows() trả về chỉ mục và hàng (dưới dạng pandas.Series) mỗi lần lặp lại.

Nhưng đối với yêu cầu của bạn, bạn có thể lặp qua df.columns và thực hiện những gì bạn muốn theo cách được vector hóa cho mỗi cột. Ví dụ -

for col in df.columns: 
    df.loc[df[col] < 0,col] += 360 
    df.loc[df[col] > 360,col] -= 360 

Tôi đang sử dụng columns thay vì rows giả định số cột sẽ ít hơn nhiều so với số lượng hàng, do đó chúng tôi sẽ làm vòng lặp thực tế cho lần lặp ít hơn nhiều (và sử dụng việc bổ sung vectorized cho đồng thời nhiều dữ liệu hơn).

Demo -

In [128]: df 
Out[128]: 
           0   1   2   3 
timestamp 
2013-04-17 05:00:00  4.335212 2655.140854 2655.140854 2655.140854 
2013-04-17 05:10:00  2.224966 2655.140854 2655.140854 2655.140854 
2013-04-17 05:20:00  2.409150 2655.140854 2655.140854 2655.140854 
2013-04-17 05:30:00 2655.140854 2655.140854 2655.140854 2655.140854 

In [134]: for col in df.columns: 
    .....:  df.loc[df[col] < 0,col] += 360 
    .....:  df.loc[df[col] > 360,col] -= 360 
    .....: 

In [135]: df 
Out[135]: 
           0   1   2   3 
timestamp 
2013-04-17 05:00:00  4.335212 2295.140854 2295.140854 2295.140854 
2013-04-17 05:10:00  2.224966 2295.140854 2295.140854 2295.140854 
2013-04-17 05:20:00  2.409150 2295.140854 2295.140854 2295.140854 
2013-04-17 05:30:00 2295.140854 2295.140854 2295.140854 2295.140854 
3

Bạn có thể sử dụng mặt nạ với whereupdate để cập nhật giá trị dataframe hiện như thế này:

In [188]: df 
Out[188]: 
           0   1   2   3 
timestamp                
2013-04-1705:00:00  4.335212 2655.140854 2655.140854 2655.140854 
2013-04-1705:10:00  2.224966 2655.140854 2655.140854 2655.140854 
2013-04-1705:20:00  2.409150 2655.140854 2655.140854 2655.140854 
2013-04-1705:30:00 2655.140854 2655.140854 2655.140854 2655.140854 

In [189]: df_small = df.where(df < 0).apply(lambda x: x + 360) 

In [190]: df_small 
Out[190]: 
        0 1 2 3 
timestamp       
2013-04-1705:00:00 NaN NaN NaN NaN 
2013-04-1705:10:00 NaN NaN NaN NaN 
2013-04-1705:20:00 NaN NaN NaN NaN 
2013-04-1705:30:00 NaN NaN NaN NaN 

In [191]: df_large = df.where(df > 360).apply(lambda x: x - 360) 

In [192]: df_large 
Out[192]: 
           0   1   2   3 
timestamp                
2013-04-1705:00:00   NaN 2295.140854 2295.140854 2295.140854 
2013-04-1705:10:00   NaN 2295.140854 2295.140854 2295.140854 
2013-04-1705:20:00   NaN 2295.140854 2295.140854 2295.140854 
2013-04-1705:30:00 2295.140854 2295.140854 2295.140854 2295.140854 

In [193]: df.update(df_small) 

In [194]: df.update(df_large) 

In [195]: df 
Out[195]: 
           0   1   2   3 
timestamp                
2013-04-1705:00:00  4.335212 2295.140854 2295.140854 2295.140854 
2013-04-1705:10:00  2.224966 2295.140854 2295.140854 2295.140854 
2013-04-1705:20:00  2.409150 2295.140854 2295.140854 2295.140854 
2013-04-1705:30:00 2295.140854 2295.140854 2295.140854 2295.140854 

Lưu ý:

Điều này sẽ có khả năng phục vụ các trường hợp góc nếu bạn tình cờ có các điều kiện như: "giá trị" < 360 rồi +360 khác -360 nhưng trình tự cập nhật sẽ khiến kết quả được áp dụng lại, tức là. 1 + 360 = 361, rồi 361> 360 để nó trở thành 1 lần nữa.

Nhưng đối với trường hợp sử dụng của bạn, tôi nghĩ rằng phương pháp của @ AnandSKumar rất sạch sẽ và gần với những gì bạn đang tìm kiếm.

Các vấn đề liên quan