虚拟/分类变量线性回归

2024-05-16 05:24:26 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一组数据。我已经使用pandas将它们分别转换为伪变量和分类变量。所以,现在我想知道,如何在Python中运行一个多元线性回归(我使用的是statsmodels)?。有什么需要考虑的吗?或者我必须指出变量在我的代码中是伪的/分类的?或者,变量的转换就足够了,我只需要以model = sm.OLS(y, X).fit()的形式运行回归?。

我的代码如下:

datos = pd.read_csv("datos_2.csv")
df = pd.DataFrame(datos)
print(df)

我明白了:

Age  Gender    Wage         Job         Classification 
32    Male  450000       Professor           High
28    Male  500000  Administrative           High
40  Female   20000       Professor            Low
47    Male   70000       Assistant         Medium
50  Female  345000       Professor         Medium
27  Female  156000       Assistant            Low
56    Male  432000  Administrative            Low
43  Female  100000  Administrative            Low

然后我做:1=男性,0=女性,1:教授,2:行政,3:助理这边:

df['Sex_male']=df.Gender.map({'Female':0,'Male':1})
        df['Job_index']=df.Job.map({'Professor':1,'Administrative':2,'Assistant':3})
print(df)

得到这个:

 Age  Gender    Wage             Job Classification  Sex_male  Job_index
 32    Male  450000       Professor           High         1          1
 28    Male  500000  Administrative           High         1          2
 40  Female   20000       Professor            Low         0          1
 47    Male   70000       Assistant         Medium         1          3
 50  Female  345000       Professor         Medium         0          1
 27  Female  156000       Assistant            Low         0          3
 56    Male  432000  Administrative            Low         1          2
 43  Female  100000  Administrative            Low         0          2

现在,如果我运行一个多元线性回归,例如:

y = datos['Wage']
X = datos[['Sex_mal', 'Job_index','Age']]
X = sm.add_constant(X)
model1 = sm.OLS(y, X).fit()
results1=model1.summary(alpha=0.05)
print(results1)

结果显示正常,但可以吗?或者我必须以某种方式指出变量是虚拟的还是分类的?。请帮忙,我是Python新手,我想学习。来自南美-智利的问候。


Tags: dfage分类jobmalefemalelowmedium
2条回答

您需要指出JobJob_index是一个分类变量;否则,在Job_index的情况下,它将被视为一个连续变量(刚好取123),这是不对的。

您可以在statsmodels中使用几种不同的符号,下面是公式方法,它使用C()来表示分类变量:

from statsmodels.formula.api import ols

fit = ols('Wage ~ C(Sex_male) + C(Job) + Age', data=df).fit() 

fit.summary()

                            OLS Regression Results                            
==============================================================================
Dep. Variable:                   Wage   R-squared:                       0.592
Model:                            OLS   Adj. R-squared:                  0.048
Method:                 Least Squares   F-statistic:                     1.089
Date:                Wed, 06 Jun 2018   Prob (F-statistic):              0.492
Time:                        22:35:43   Log-Likelihood:                -104.59
No. Observations:                   8   AIC:                             219.2
Df Residuals:                       3   BIC:                             219.6
Df Model:                           4                                         
Covariance Type:            nonrobust                                         
=======================================================================================
                          coef    std err          t      P>|t|      [0.025      0.975]
---------------------------------------------------------------------------------------
Intercept             3.67e+05   3.22e+05      1.141      0.337   -6.57e+05    1.39e+06
C(Sex_male)[T.1]     2.083e+05   1.39e+05      1.498      0.231   -2.34e+05    6.51e+05
C(Job)[T.Assistant] -2.167e+05   1.77e+05     -1.223      0.309    -7.8e+05    3.47e+05
C(Job)[T.Professor] -9273.0556   1.61e+05     -0.058      0.958   -5.21e+05    5.03e+05
Age                 -3823.7419   6850.345     -0.558      0.616   -2.56e+04     1.8e+04
==============================================================================
Omnibus:                        0.479   Durbin-Watson:                   1.620
Prob(Omnibus):                  0.787   Jarque-Bera (JB):                0.464
Skew:                          -0.108   Prob(JB):                        0.793
Kurtosis:                       1.839   Cond. No.                         215.
==============================================================================

注意:JobJob_index不会使用相同的分类级别作为基线,因此您将看到每个级别的虚拟系数略有不同的结果,即使整个模型拟合保持不变。

在带有分类变量的线性回归中,您应该小心伪变量陷阱。虚拟变量陷阱是一种自变量是多重共线性的情况,即两个或多个变量高度相关的情况;简单地说,一个变量可以从其他变量中预测出来。这会产生模型的奇点,这意味着你的模型无法工作。Read about it here

其思想是对drop_first=True使用伪变量编码,这将在将分类变量转换为伪/指示符变量之后从每个类别中省略一列。这样做不会丢失相关信息,因为数据集中的所有点都可以由其他特性完全解释。

以下是有关如何为作业数据集执行此操作的完整代码

所以你有你的X特征:

Age, Gender, Job, Classification 

还有一个你想预测的数字特征:

Wage

首先,您需要在输入变量和预测上拆分初始数据集,假设它的pandas数据帧如下所示:

输入变量(您的数据集有点不同,但整个代码保持不变,您将把数据集中的每一列放在X中,除了一列将转到Y.pd。get_dummies工作正常,没有问题-它将只转换分类变量,不会接触数字):

X = jobs[['Age','Gender','Job','Classification']]

预测:

Y = jobs['Wage']

将分类变量转换为伪/指示符变量,并在每个类别中删除一个:

X = pd.get_dummies(data=X, drop_first=True)

所以现在如果你用drop_first=True检查X的形状(X.shape),你会发现它少了4列,每个分类变量少了一列。

现在可以继续在线性模型中使用它们。对于scikit learn实现,它可能如下所示:

from sklearn import linear_model
from sklearn.model_selection import train_test_split
    X_train, X_test, Y_train, Y_test = train_test_split(X, Y, test_size = .20, random_state = 40)
        regr = linear_model.LinearRegression() # Do not use fit_intercept = False if you have removed 1 column after dummy encoding
        regr.fit(X_train, Y_train)
    predicted = regr.predict(X_test)

相关问题 更多 >