2017-11-09 4 views
1

다음 작업을 수행하고 싶습니다. 2 열 (좋고 나쁨)을 감안할 때 두 열에 대한 행을 누적으로 대체하고 싶습니다. 다음은 원하는 데이터 프레임과 함께 현재 데이터 프레임의 예제입니다.Python Pandas가 재설정시 합계를 실행 중입니다.

편집 : 내 의도가 무엇인지 추가해야합니다. 연속 변수를 입력으로 사용하여 binned (이 경우 20) 변수를 동일하게 만들기 위해 노력하고 있습니다. 나는 pandas cut과 qcut 함수를 사용할 수 있지만 반환 된 결과는 좋은/나쁜 비율 (증거 및 정보 값의 가중치를 계산하는 데 필요함)에 대해 0을 갖습니다. 분자 또는 분모의 0은 수학 계산을 허용하지 않습니다.

d={'AAA':range(0,20), 
     'good':[3,3,13,20,28,32,59,72,64,52,38,24,17,19,12,5,7,6,2,0], 
     'bad':[0,0,1,1,1,0,6,8,10,6,6,10,5,8,2,2,1,3,1,1]} 
    df=pd.DataFrame(data=d) 
    print(df) 

다음은 위 데이터 프레임에 대한 설명입니다. enter image description here

어느 열에 대해서도 0이 발생할 때마다 0이 포함 된 열의 값이 0이 아닌 다음 행까지는 0이 아닌 열에 대해 누적 합계를 사용해야합니다.

dd={'AAA':range(0,16), 
    'good':[19,20,60,59,72,64,52,38,24,17,19,12,5,7,6,2], 
    'bad':[1,1,1,6,8,10,6,6,10,5,8,2,2,1,3,2]} 

desired_df=pd.DataFrame(data=dd)  
print(desired_df) 
+0

는 I은 쉽게 다음 행 (59) 및 출력 (32)의 양호한 값을 추가하는 경우, 프로그래밍, 말하자면 60해야 명시된 그 = 로우 (6 = 나쁜 좋은 32 + 59 = 81)도 작동합니다. – Kyle

답변

0

내 용액의 기본적인 아이디어는 다음의 영이 아닌 값으로하여 0 값을 얻기 위해 비 - 제로 값 위에 cumsum에서 열을 생성하는 것이다 : 여기

원하는 출력 하나의 그룹. 그런 다음 groupby + sum을 사용하여 원하는 값을 얻을 수 있습니다.

two_good = df.groupby((df['bad']!=0).cumsum().shift(1).fillna(0))['good'].sum() 
two_bad = df.groupby((df['good']!=0).cumsum().shift(1).fillna(0))['bad'].sum() 

two_good = two_good.loc[two_good!=0].reset_index(drop=True) 
two_bad = two_bad.loc[two_bad!=0].reset_index(drop=True) 

new_df = pd.concat([two_bad, two_good], axis=1).dropna() 
print(new_df) 
    bad good 
0  1 19.0 
1  1 20.0 
2  1 28.0 
3  6 91.0 
4  8 72.0 
5 10 64.0 
6  6 52.0 
7  6 38.0 
8 10 24.0 
9  5 17.0 
10 8 19.0 
11 2 12.0 
12 2 5.0 
13 1 7.0 
14 3 6.0 
15 1 2.0 

이 코드는 원하는 출력과 다른 후행 0의 에칭 사례를 처리합니다. 간단하게 잘라냅니다. 다른 로직을 가진 코드를 잡으려면 추가 코드를 추가해야합니다.

+0

이것은 유망 해 보인다. (수학으로 깨닫다 (32 + 59 = 81은 91이어야 했음)). 내가 보는 유일한 문제는 마지막 빈, 색인 = 15, 나쁜 = 1, 좋은 = 2입니다. 이 저장소는 bad = 2 (이전 행과 현재 행) 및 good = 2 (명시된 것)에 대한 값을 가져야합니다. – Kyle

+0

그게 마지막 두 문장과 무슨 의미인지 알 수 있습니다. 여기서 문제는 일반적으로 다음 0이 아닌 값을 합산하려고하지만 마지막 값이 0이면 다음 0이 아닌 값이없는 것입니다. 이를 처리하기 위해 추가 코드를 추가해야합니다. –

0

P.Tillmann. 도와 주셔서 감사합니다. 더 고급 독자를 위해 나는이 코드를 소름 끼치는 것으로 생각할 것입니다. 좀 더 간소화 된 제안을하는 것이 기쁠 것입니다. 행에 대한

d={'AAA':range(0,20), 
    'good':[3,3,13,20,28,32,59,72,64,52,38,24,17,19,12,5,7,6,2,0], 
    'bad':[0,0,1,1,1,0,6,8,10,6,6,10,5,8,2,2,1,3,1,1]} 
df=pd.DataFrame(data=d) 
print(df) 

row_good=0 
row_bad=0 
row_bad_zero_count=0 
row_good_zero_count=0 
row_out='NO' 
crappy_fix=pd.DataFrame() 
for index,row in df.iterrows(): 
    if row['good']==0 or row['bad']==0: 
     row_bad += row['bad'] 
     row_good += row['good'] 
     row_bad_zero_count += 1 
     row_good_zero_count += 1 
     output_ind='1' 
     row_out='NO' 
    elif index+1 < len(df) and (df.loc[index+1,'good']==0 or df.loc[index+1,'bad']==0): 
     row_bad=row['bad'] 
     row_good=row['good'] 
     output_ind='2' 
     row_out='NO'  
    elif (row_bad_zero_count > 1 or row_good_zero_count > 1) and row['good']!=0 and row['bad']!=0: 
     row_bad += row['bad'] 
     row_good += row['good'] 
     row_bad_zero_count=0 
     row_good_zero_count=0  
     row_out='YES' 
     output_ind='3' 
    else: 
     row_bad=row['bad'] 
     row_good=row['good'] 
     row_bad_zero_count=0 
     row_good_zero_count=0 
     row_out='YES' 
     output_ind='4' 

    if ((row['good']==0 or row['bad']==0) 
     and (index > 0 and (df.loc[index-1,'good']!=0 or df.loc[index-1,'bad']!=0)) 
     and row_good != 0 and row_bad != 0): 
     row_out='YES' 

    if row_out=='YES': 
     temp_dict={'AAA':row['AAA'], 
        'good':row_good, 
        'bad':row_bad} 
     crappy_fix=crappy_fix.append([temp_dict],ignore_index=True) 
     print(str(row['AAA']),'-', 
       str(row['good']),'-', 
       str(row['bad']),'-', 
       str(row_good),'-', 
       str(row_bad),'-', 
       str(row_good_zero_count),'-', 
       str(row_bad_zero_count),'-', 
       row_out,'-', 
       output_ind) 

print(crappy_fix) 
관련 문제