регрессионный анализ панд - PullRequest
0 голосов
/ 01 октября 2019

У меня есть набор данных, похожий на:

import numpy as np
import statsmodels.api as sm
import statsmodels.formula.api as smf
dat = sm.datasets.get_rdataset("Guerry", "HistData").data

results = []
def fit_model_and_get_results(formula, data):
    model = smf.ols(formula, data=data).fit()
    #print(model.summary())
    this_run = {}
    this_run['model'] = formula

    model_df = model.summary2().tables[1]
    quality_tables = model.summary2().tables[0]
    quality_tables.columns = [quality_tables.columns % 2, quality_tables.columns // 2]
    quality_tables = quality_tables.stack().reset_index(drop=True)
    quality_tables.columns = ['metric_kind', 'metric_value']
    quality_tables = quality_tables[quality_tables.metric_kind != '']

    for index, row in quality_tables.iterrows():
         this_run[row.metric_kind] = row.metric_value

    for k, v in this_run.items():
         model_df[k] = v
    return model_df


current_result = fit_model_and_get_results('Lottery ~ Literacy', dat)
current_result['variant'] = 'single_variable'
results.append(current_result)

current_result = fit_model_and_get_results('Lottery ~ Crime_pers', dat)
current_result['variant'] = 'single_variable'
results.append(current_result)

current_result = fit_model_and_get_results('Lottery ~ Crime_prop', dat)
current_result['variant'] = 'single_variable'
results.append(current_result)

# ***********************************************************************************
# adjustment for literacy
current_result = fit_model_and_get_results('Lottery ~ Literacy + Crime_pers', dat)
current_result['variant'] = 'two_variables'
results.append(current_result)

current_result = fit_model_and_get_results('Lottery ~ Literacy + Crime_prop', dat)
current_result['variant'] = 'two_variables'
results.append(current_result)

results = pd.concat(results)
#results = results.reset_index()
display(results)

, который выглядит следующим образом: enter image description here т.е. одна переменная в модели представляет собой наблюдение, а фрейм данных содержит несколько моделей.

Однако, чтобы иметь возможность лучше сравнивать результаты, я хотел бы получить результат, подобный следующему: enter image description here, где каждая переменная присутствует один раз (как одно наблюдение), но несколько моделей составляютстолбцы.

Похоже, что требуется поворот. Однако до сих пор я не нашел правильного способа его выполнения.

Требуемый результат должен содержать:

  • переменную в качестве первого столбца с одной строкой для каждой переменной
  • , а затем каждая модель в виде отдельного столбца, в котором достаточно сохранить только коэффициент регрессии, значение t и значение p

edit

Несколько регрессийдолжно быть легко сопоставимым. Т.е. как только все 1 комбинации затем корректируются для некоторых признаков (пол, пол), а затем снова рассчитываются все оставшиеся отдельные комбинации с добавленными этими признаками для корректировки, а затем одна третья модель, где все признаки используются для прогнозирования.

Т.е. в этом случае сначала все 1 комбинации (Грамотность, Crime_pers) рассчитываются как отдельные (одиночные) модели. Затем он корректируется с учетом грамотности, а остальные (только Crime_pers) рассчитываются. Упомянутая выше 3-я модель опущена, чтобы сохранить пример минимальным.

В соответствии с запросом выходной примерный кадр данных для первых двух случаев:

d = pd.DataFrame({'feature':['Crime_pers', 'Literacy'], 'single_variable': [[4,4,6],[2,6,3]], 'two_variables' : [
    #coef, t, p
    np.nan,
    [2,3,4]]})
display(d)
print(d)
      feature single_variable two_variables
0  Crime_pers       [4, 4, 6]           NaN
1    Literacy       [2, 6, 3]     [2, 3, 4]

Где подколонки в каждомполя являются (коэффициент, t-значение, p-значение (в настоящее время они не содержат реальных значений только что составленных значений для краткости)). Для записи 0 и two_variables выходное значение равно NaN, поскольку релевантными являются только значения для моделей, которые не были явно скорректированы.

В основном вышеприведенный результат показывает результаты всех 3 моделей, которые были установленыв очень сжатом формате.

edit 2

Я обновил минимальный пример, так как он был слишком минималистичным. К сожалению, я застрял с:

ValueError: Index contains duplicate entries, cannot reshape

при применении предложенного шага разворота

1 Ответ

1 голос
/ 01 октября 2019

Боюсь, я не понимаю, что выбрать для таблицы конечных результатов, но, возможно, это поможет вам адаптировать ее по мере необходимости:

res = pd.DataFrame(results.loc[results.index!='Intercept','variant'])
res['val'] = results.loc[results.index!='Intercept',['Coef.', 'P>|t|', 't']].apply(lambda x: list(map('{:.3f}'.format, list(x))), axis=1)
res = res[(res.index=='Literacy') | (res.variant=='single_variable')].pivot(columns='variant')

Результат:

                                val                         
variant             single_variable            two_variables
Crime_pers    [0.000, 0.981, 0.024]                      NaN
Literacy    [-0.524, 0.001, -3.590]  [-0.525, 0.001, -3.570]
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...