StatsModels的Numpy.dot点乘积函数

时间:2019-01-17 22:27:57

标签: python arrays numpy linear-regression linear-algebra

我正在学习statsmodels.api模块以使用python进行回归分析。因此,我从简单的OLS模型开始。

在计量经济学中,该函数类似于:y = Xb + e 其中X是NxK维度,b是Kx1,e是Nx1,因此将y加在一起是Nx1。从线性代数的角度来看,这是完全可以的。

但是我遵循了Statsmodels的教程,内容如下:

import numpy as np
nsample = 100 # total obs is 100
x = np.linspace(0, 10, 100) # using np.linspace(start, stop, number)

X = np.column_stack((x, x**2))
beta = np.array([1, 0.1, 10])

e = np.random.normal(size = nsample) # draw numbers from normal distribution 
default at mu = 0, and std.dev = 1, size = set by user
# e is n x 1
# Now, we add the constant/intercept term to X
X = sm.add_constant(X)
# Now, we compute the y
y = np.dot(X, beta) + e

因此,这将生成正确的答案。但是我对beta = np.array([1,0.1,10])的生成有疑问。如果使用此Beta,则:

beta.shape
(3,)

它的尺寸为(3,),y和e相同,除了X:

X.shape
(100,3)
e.shape
(100,)
y.shape
(100,)

所以我猜想通过以下三种方式来初始化数组

o = array([1,2,3])
o1 = array([[1],[2],[3]])
o2 = array([[1,2,3]])
print(o.shape)
print(o1.shape)
print(o2.shape)
----------------
(3,)
(3, 1)
(1, 3)

如果我使用beta = array([[1],[2],[3]]),它是(3,1),而np.dot(X,beta)给我一个错误的答案,尽管尺寸似乎有效。 如果我使用array([[1,2,3]])(这是行向量),则该尺寸与numpy中的点积不匹配,在线性代数中也不匹配。

所以,我想知道为什么对于NxK点Kx1 numpy点乘积,我们必须使用(N,K)点(K,)而不是(N,K)点(K,1)矩阵。什么操作只能使np.array([1,0.1,10])适用于numpy.dot(),而np.array([[1],[0.1],[10]])无效。

非常感谢您。


一些更新

抱歉,Statsmodels中的代码是随机生成的,因此我尝试修复X并获得以下输入:

f = array([[1,2,3],[4,5,6],[7,8,9],[10,11,12],[13,14,15]])
o = array([1,2,3])
o1 = array([[1],[2],[3]])
o2 = array([[1,2,3]])
print(o.shape)
print(o1.shape)
print(o2.shape)
print("---------")
print(np.dot(f,o))
print(np.dot(f,o1))
r1 = np.dot(f,o)
r2 = np.dot(f,o1)
type1 = type(np.dot(f,o))
type2 = type(np.dot(f,o1))
tf = type1 is type2
tf2 = type1 == type2
print(type1)
print(type2)
print(tf)
print(tf2)
-------------------------
(3,)
(3, 1)
(1, 3)
---------
[14 32 50 68 86]
[[14]
 [32]
 [50]
 [68]
 [86]]
<class 'numpy.ndarray'>
<class 'numpy.ndarray'>
True
True

再次抱歉给您带来的混乱和不便,他们的工作很好。

1 个答案:

答案 0 :(得分:1)

python / numpy不是基于矩阵的语言,因为它是Matlab或Octave或Scilab。这些严格遵循矩阵乘法的规则。所以

np.dot(f,o)  ---------> f*o  in Matlab/Octave/Scilab
np.dot(f,o1) ---------> f*o1 does not work in Matlab/Octave/Scilab

python / numpy具有“广播”功能,这些规则是不同数据类型和操作如何将结果汇总在一起的规则。尽管np.dot(f,o1)为何也应该工作还不清楚,但是广播定义了一些有用的结果。您将需要为此查阅文档。

在python / numpy中,*不是矩阵运算符。您可以找出广播的目的

print(f*o)
print(f*o1)
print(f*o2)

最近,python / numpy引入了矩阵运算符@ 。您可能会发现发生了什么

print(f@o)
print(f@o1)
print(f@o2)

这会给人一些印象吗?