Панды - показать процент значений в одном столбце, сгруппированных по другому столбцу - PullRequest
0 голосов
/ 05 сентября 2018

Итак, у меня есть DataFrame Pandas с двумя столбцами: Первый класс с значениями от 0 до 9 второй критерий, со значениями 0 или 1.

Оценка (0-9 / Критерии (0/1)

   Grade  Criteria
0      0         1
1      1         0
2      2         1
3      2         0
4      5         1
5      2         1

и т.д.

Мне нужно сосчитать «показатель критериев», который фактически является суммой «1» в столбце «Критерии», деленной на соответствующее количество строк в столбце «Критерии», но сгруппированных по значениям столбца «Класс». Например, для степени 2 мы считаем сумму 1 в столбце Критерии и делим ее на количество строк в классе 2: 2/3, поэтому для степени 2 получаем 0,66 приблиз. В моем примере ответ должен выглядеть так:

Оценка / критерий оценки

   Grade  Criteria
0      0  1.000000
1      1  0.000000
2      2  0.666667
3      5  1.000000

Есть идеи, как это сделать? Также доп. вопрос - как это сделать, если в столбце Критерии есть текстовые значения «да / нет»? Я искал здесь, но нашел только решения для groupby's, разделенные на общее количество строк и т. Д.

Спасибо!

Ответы [ 2 ]

0 голосов
/ 05 сентября 2018

Если критерий равен 1 или 0, или даже True или False

Вы можете использовать mean

groupby

df.groupby('Grade').mean()

       Criteria
Grade          
0      1.000000
1      0.000000
2      0.666667
5      1.000000

set_index и mean

df.set_index('Grade').mean(level=0)

       Criteria
Grade          
0      1.000000
1      0.000000
2      0.666667
5      1.000000

В случае, если 'Criteria' являются 'yes' и 'no' строками

df

   Grade Criteria
0      0      yes
1      1       no
2      2      yes
3      2       no
4      5      yes
5      2      yes

Вы можете сгруппировать логическую оценку

df.Criteria.eq('yes').groupby(df.Grade).mean()

Grade
0    1.000000
1    0.000000
2    0.666667
5    1.000000
Name: Criteria, dtype: float64

Используйте reset_index на любом из этих ответов, чтобы получить нужный кадр данных

0 голосов
/ 05 сентября 2018

Вы можете объединить sum с size и затем разделить столбцы:

df = df.groupby('Grade')['Criteria'].agg(['sum','size'])
df['new'] = df['sum'] / df['size']
print (df)
       sum  size       new
Grade                     
0        1     1  1.000000
1        0     1  0.000000
2        2     3  0.666667
5        1     1  1.000000

Или используйте пользовательскую функцию:

#not exclude NaNs 
df = df.groupby('Grade')['Criteria'].agg(lambda x: x.sum() / len(x)).reset_index(name='new')

#exclude possible NaNs
df = df.groupby('Grade')['Criteria'].agg(lambda x: x.sum() / x.count()).reset_index(name='new')

Для yes/no значений, работающих с логической маской - True s - это процессы, подобные 1 s:

print (df)
   Grade Criteria
0      0      yes
1      1       no
2      2      yes
3      2       no
4      5      yes
5      2      yes

df = (df['Criteria'] == 'yes').groupby(df['Grade']).agg(lambda x: x.sum() / len(x)).reset_index(name='new')
print (df)
   Grade       new
0      0  1.000000
1      1  0.000000
2      2  0.666667
3      5  1.000000
...