【问题标题】:How to approximate a function with a neural net如何用神经网络逼近一个函数
【发布时间】:2020-12-28 15:59:44
【问题描述】:

学习神经网络我编写了自己的课程。

import numpy as np
import random


def sigmoid(x):
    return 1.0 / (1.0 + np.exp(-x))


def sigmoid_prime(x):
    return sigmoid(x) * (1 - sigmoid(x))


def linear(x):
    return x

def linear_prime(x):
    return 1

def tanh(x):
    return (np.exp(x) - np.exp(-x))/(np.exp(x) + np.exp(-x))

def tanh_prime(x):
    return 1 - tanh(x)*tanh(x)

class Network:
    def __init__(self, sizes, activation_func = sigmoid, activation_prime = sigmoid_prime):
        
        self.biases = [np.random.randn(x, 1) for x in sizes[1:]]
        self.weights = [np.random.randn(y, x) for x, y in zip(sizes, sizes[1:])]

        self.num_layers = len(sizes)
        self.sizes = sizes

        self.activation_function = activation_func
        self.actiovation_prime = activation_prime

    def forward_prop(self, a):
        for w, b in zip(self.weights, self.biases):
            a = self.activation_function(np.dot(w, a) + b)
        return a

    def cost_derivative(self, output_activations, y):
        return (output_activations - y)

    def backprop(self, x, y):

        nabla_b = [np.zeros(b.shape) for b in self.biases]
        nabla_w = [np.zeros(w.shape) for w in self.weights]

        # forward pass

        activation = x  # first activation, which is input layer
        a_mas = [x]
        z_mas = []

        for b, w in zip(self.biases, self.weights):
            z = np.dot(w, activation) + b
            activation = self.activation_function(z)
            z_mas.append(z)
            a_mas.append(activation)
            pass

        # backward pass
        
        delta = self.cost_derivative(a_mas[-1], y) * self.actiovation_prime(z_mas[-1])
        nabla_b[-1] = delta
        nabla_w[-1] = np.dot(delta, a_mas[-2].T)

        for l in range(2, self.num_layers):  # there is 2 such as we've already done for last layer

            delta = np.dot(self.weights[-l + 1].transpose(), delta) * self.actiovation_prime(z_mas[-l])
            nabla_b[-l] = delta
            nabla_w[-l] = np.dot(delta, a_mas[-l - 1].T)

        return nabla_b, nabla_w

    def update_mini_batch(self, mini_batch, eta):

        nabla_b = [np.zeros(b.shape) for b in self.biases]
        nabla_w = [np.zeros(w.shape) for w in self.weights]

        for x, y in mini_batch:
            delta_nabla_b, delta_nabla_w = self.backprop(x, y)
            nabla_b = [nb + dnb for nb, dnb in zip(nabla_b, delta_nabla_b)]
            nabla_w = [nw + dnw for nw, dnw in zip(nabla_w, delta_nabla_w)]

        eps = eta / len(mini_batch)
        self.weights = [w - eps * nw for w, nw in zip(self.weights, nabla_w)]
        self.biases = [b - eps * nb for b, nb in zip(self.biases, nabla_b)]

    def SGD(self, training_data, epochs, mini_batch_size, eta):
        n = len(training_data)

        for j in range(epochs):
            random.shuffle(training_data)
            mini_batches = [training_data[k:k + mini_batch_size]
                            for k in range(0, n, mini_batch_size)]

            for mini_batch in mini_batches:
                self.update_mini_batch(mini_batch, eta)

现在我正在尝试借助这个网络来近似 sin()。但是下面的代码不能正常工作。

%matplotlib inline
import matplotlib.pyplot as plt

net2 = Network([1,100,1],tanh,tanh_prime)

x = np.linspace(0,10,1000)
y = np.sin(x)



train = [(np.array(x[i]).reshape(1,1),np.array(y[i]).reshape(1,1)) for i in range(len(x))]
    
    
net2.SGD(train,10,10,0.1)

y_pred = []
y_tmp = []

for i in range(len(x)):
    y_tmp.append(net2.forward_prop(train[i][0]))
    y_pred.append(float(net2.forward_prop(train[i][0])))


plt.plot(x,y_look,'r',x,y_pred)
plt.grid()

这是我得到的。

我已经尝试在 MNIST 数据集的帮助下在数字识别中实现这个网络。那里一切正常。但是我无法获得比 70% 更好的准确度,但这不是问题。但是这里我不知道出了什么问题...激活函数是 tanh()。

【问题讨论】:

    标签: python neural-network approximation


    【解决方案1】:

    据我所知,您正在最小化函数 f(x) - y,您可能希望将其更改为均方误差 ((f(x) - y)^2) 或平均绝对误差 (|f(x) - y|),这足以解决回归问题,例如你的。对于 MNIST 这样的分类问题,交叉熵是一个不错的选择。

    另外,您可以尝试删除输出层中的 tanh 函数。我不认为tanh 是个问题,因为输出介于 -1 和 1 之间,但通常,对于回归问题,我们使用线性激活,并且我们会继续压缩函数,例如 sigmoid 和 tanh 来解决分类问题。

    【讨论】:

    • 感谢您的帮助。一旦我得到解决方案并了解问题所在,我会在这里写信。
    • @qneeus 顺便说一句,我正在最小化 MSE 函数。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-12-03
    • 2018-09-10
    • 2013-04-14
    • 2017-04-01
    • 1970-01-01
    • 1970-01-01
    • 2017-11-26
    相关资源
    最近更新 更多