我正尝试用Python (使用Numpy)从头开始实现一个神经网络模型。作为参考,我正在借鉴这本书 (从数据中学习)的第e-7章作为理论支持。
我面临的第一个问题是如何正确地初始化权值矩阵以及输入和输出的向量(分别是W、x和s )。
以下是我的方法:
L是层数(您不计算‘第一个’层;即向量x的层加上‘偏差’)。d是隐藏层的维度(我假设所有隐藏层都有相同数量的节点)。out设为最后一层的节点数(通常为1)。下面是我如何定义矩阵和感兴趣的向量:
w_是权值的向量。实际上,它是一个向量,其中每个分量都是W_{L}形式的矩阵。这里,(i,j)-th值是w_{i,j}{(L)}}项。x_作为输入的向量。s_成为输出的向量;您可以将s_看作numpy.dot(W^{L}.T, x^{L-1})。下面的图片总结了我刚才描述的内容:

问题产生于这样一个事实,即每个层(输入、隐藏层和输出)的维度并不相同。我想要做的是将每个向量分割成不同的变量;但是,在算法的以下步骤中使用它是非常困难的(因为索引是如何变得一团糟的)。下面是复制我的尝试的代码:
class NeuralNetwork:
"""
Neural Network Model
"""
def __init__(self, L, d, out):
self.L = L # number of layers
self.d = d # dimension of hidden layers
self.out = out # dimension of the output layer
def initialize_(self, X):
# Initialize the vector of inputs
self.x_ = np.zeros((self.L - 1) * (self.d + 1)).reshape(self.L - 1, self.d + 1)
self.xOUT_ = np.zeros(1 * self.out).reshape(1, self.out)
# Initialize the vector of outputs
self.s_ = np.zeros((self.L - 1) * (self.d)).reshape(self.L - 1, self.d)
self.sOUT_ = np.zeros(1 * self.out).reshape(1, self.out)
# Initialize the vector of weights
self.wIN_ = np.random.normal(0, 0.1, 1 * (X.shape[1] + 1) * self.d).reshape(1, X.shape[1] + 1, self.d)
self.w_ = np.random.normal(0, 0.1, (self.L - 2) * (self.d + 1) * self.d).reshape(self.L - 2, self.d + 1, self.d)
self.wOUT_ = np.random.normal(0, 0.1, 1 * (self.d + 1) * self.out).reshape(1, self.d + 1, self.out)
def fit(self, X, y):
self.initialize_(X)每当IN或OUT出现在代码中时,我就可以分别处理输入层和输出层之间的维度差异。
显然,这不是一个很好的方法。所以我的问题是:我如何以一种聪明的方式处理这些不同的维向量(相对于每一层)?
例如,在初始化它们之后,我希望复制以下算法(前向传播)--您将看到,用我的索引方式,这几乎是不可能的:

其中θ= \tanh(s)。
P.S.:我也尝试创建数组(或列表数组),但是如果这样做,我的索引就会变得无用--它们不再代表我希望它们表示的内容。
发布于 2020-01-01 08:04:16
您可以封装神经元逻辑,让神经元单独执行计算:
class Neuron:
def __init__(self, I, O, b):
self.I = I # input neurons from previous layer
self.O = O # output neurons in next layer
self.b = b # bias
def activate(self, X):
output = np.dot(self.I, X) + self.b
...
return theta(output)https://stackoverflow.com/questions/59550711
复制相似问题