【问题标题】:How do I implement the function f(x) = { x^2, x>0 and -x^2 , x<0 } for a numpy array 'x'?如何为 numpy 数组“x”实现函数 f(x) = { x^2, x>0 和 -x^2 , x<0 }?
【发布时间】:2020-11-04 11:43:20
【问题描述】:

我正在尝试根据以下函数更改 Numpy 数组“x”中的每个值:

f(x) = { x^2 , x >= 0 and 
        -x^2 , x < 0  }
@numpy.vectorize
def squares(x):
    return (x ** 2) if x >= 0 else -(-x ** 2)

该函数似乎已正确执行,但是当结果用于此时

tmp = output_errors * output_network * (1.0 - output_network)

稍后,它显示以下错误:RuntimeWarning: overflow encountered in multiply

但是,运行以下代码时没有出现此类错误:

@numpy.vectorize
def sigmoid(x):
    return 1 / (1 + numpy.e ** -x)

整个代码是

import time
import pickle
from scipy.stats import truncnorm
from datetime import datetime

@numpy.vectorize
def activate(x):
    negative_mask = x < 0
    x = x ** 2
    x[negative_mask] *= -1
    return x
    #return (x ** 2) if x > 0 else (-(x ** 2))
    
def truncated_normal(mean=0, sd=1, low=0, upp=10):
    return truncnorm((low - mean) / sd, (upp - mean) / sd, loc=mean, scale=sd)

def create_weight_matrices(no_of_in_nodes, no_of_out_nodes, no_of_hidden_nodes):
    rad = 1 / numpy.sqrt(no_of_in_nodes)
    X = truncated_normal(mean=0, sd=1, low=-rad, upp=rad)
    wih = X.rvs((no_of_hidden_nodes, no_of_in_nodes)) # Weight from Input to Hidden Layer
    
    rad = 1 / numpy.sqrt(no_of_hidden_nodes)
    X = truncated_normal(mean=0, sd=1, low=-rad, upp=rad)
    who = X.rvs((no_of_out_nodes, no_of_hidden_nodes)) # Weight from Hidden to Output Layer
    return wih, who

def train(wih, who, learning_rate, input_vector, target_vector):
    input_vector = numpy.array(input_vector, ndmin=2).T # Input Vector needs to be Transposed
    target_vector = numpy.array(target_vector, ndmin=2).T # Target Vector needs to be Transposed
    
    output_hidden = activate(numpy.dot(wih, input_vector))
    output_network = activate(numpy.dot(who, output_hidden))
    
    output_errors = target_vector - output_network
    tmp = output_errors * output_network * (1.0 - output_network)     
    who += learning_rate  * numpy.dot(tmp, output_hidden.T)

    hidden_errors = numpy.dot(who.T, output_errors)
    tmp = hidden_errors * output_hidden * (1.0 - output_hidden)
    wih += learning_rate * numpy.dot(tmp, input_vector.T)

    return wih, who

def identify(wih, who, input_vector):
    input_vector = numpy.array(input_vector, ndmin=2).T

    output_vector = numpy.dot(wih, input_vector)
    output_vector = activate(output_vector)
    
    output_vector = numpy.dot(who, output_vector)
    output_vector = activate(output_vector)

    return output_vector

image_size = 28 # Specified for the MNIST Dataset
no_of_different_labels = 10 # The Numbers from 0 to 9
image_pixels = image_size * image_size
data_path = "C:/Users/HP/Desktop/Athul/Academics B.Tech/Semester 6/Introduction to Data Communication/Mini Project - Digit Recognition/"

# MNIST Dataset has been pickled to make access faster!!!!
with open(data_path + "pickled_mnist.pkl", "br") as fh:
    data = pickle.load(fh)

train_imgs = data[0]
test_imgs = data[1]
train_labels = data[2]
test_labels = data[3]
train_labels_one_hot = data[4]
test_labels_one_hot = data[5]

no_of_in_nodes = image_pixels
no_of_out_nodes = 10 
no_of_hidden_nodes = 100
learning_rate = 0.2

#Create Weighted Matrix
wih, who = create_weight_matrices(no_of_in_nodes, no_of_out_nodes, no_of_hidden_nodes) #Create a Matrix to store the weights between Nodes

# Train the Neural Network (Assign Values to Weighted Matrix using the whole MNIST Dataset)
print("Initiating Training...")
#print(numpy.unique(train_imgs))
start_time = datetime.now()
for i in range(int(len(train_imgs[:1000]))):
    wih, who = train(wih, who, learning_rate, train_imgs[i], train_labels_one_hot[i])
end_time = datetime.now()
print("Dataset has been Trained!!!\nTime taken = ", end = "")
print(end_time - start_time, end = "\n\n")


with open(data_path + "neural_net.pkl", "bw") as line:
    data = (wih, 
            who)
    pickle.dump(data, line)
print("Neural Net Pickled!!!!")


#Test the Neural Network using MNIST Dataset
count = 0;
max_right = 0
max_wrong = 0
min_right = 1
min_wrong = 1
for i in range(len(test_imgs)):
    result = identify(wih, who, test_imgs[i])
    if(int(test_labels[i][0]) != int(numpy.argmax(result))):
        if(max_wrong < numpy.max(result)):
            max_wrong = numpy.max(result)
        if(min_wrong > numpy.max(result)):
            min_wrong = numpy.max(result)
    else:
        count += 1;
        if(max_right < numpy.max(result)):
            max_right = numpy.max(result)
        if(min_right > numpy.max(result)):
            min_right = numpy.max(result)

accuracy = (count / len(test_imgs) ) * 100.0
print("Accuracy from testing with " + str(len(test_imgs)) + " pictures = " + str(accuracy) + "%")
max_right *= 100
max_wrong *= 100
min_right *= 100
min_wrong *= 100
print("Highest Accuracy of Right matches = " + str(max_right) + "%")
print("Highest Accuracy of Wrong matches = " + str(max_wrong) + "%")
print("Lowest Accuracy of Right matches = " + str(min_right) + "%")
print("Lowest Accuracy of Wrong matches = " + str(min_wrong) + "%")

它训练神经网络识别数字!!!

【问题讨论】:

  • if x &gt;= 0 仅在 x 是单个数字时有效,如果它是数组则无效。 Python if 是更简单的开关,而不是任何类型的迭代器。
  • 如何在 Numpy 数组上实现if???
  • 你看过x&gt;0吗?
  • OverflowError: (34, 'Result too large') 在我将 x&gt;=0 更改为 x&gt;0 时的 Return 语句中
  • 顺便说一句,电源运算符** 的优先级高于-(一元或其他),因此您的-(-x ** 2) 与x ** 2 相同。

标签: python numpy neural-network activation-function


【解决方案1】:

您可以将其用于您的功能:

def squares(x):
    return (x**2) * np.sign(x)

但是您的问题似乎来自于将大数相乘。查看您的最大/最小数字。

【讨论】:

  • 所有值都是0到1之间的浮点值!!! [0.01 0.01388235 0.01776471 0.02164706 0.02552941 0.02941176 ... 0.98835294 0.99223529 0.99611765 1.]
  • @AthulShibu output_errors 和 output_network 值是什么?
  • 它们是神经网络的一部分(问题中提供了代码)。当激活函数为 Sigmoid 时一切正常,但我想将其更改为正方形!
  • 您必须在错误发生前跟踪数组的值,以查看何时发生溢出以找到问题的根源。
【解决方案2】:

您要平方的数字有多大(或小,如果为负数)?溢出意味着没有足够的位来存储结果。您可以尝试使用具有更大 dtype 的 numpy 数组。这是一个转换现有数组的示例,或者您可以在创建时调整它的大小:

a = a.astype(numpy.float128)

对于函数,像你一样进行矢量化应该可以工作,或者:

negative_mask = a < 0
a = a ** 2
a[negative_mask] *= -1

【讨论】:

  • print(numpy.unique(train_imgs)) 给出结果[0.01 0.01388235 0.01776471 0.02164706 0.02552941 0.02941176 ... 0.98835294 0.99223529 0.996111
  • 在崩溃的行之前打印 output_network 和 output_errors 的 min() 和 max() 怎么样?
猜你喜欢
  • 2012-11-04
  • 1970-01-01
  • 1970-01-01
  • 2021-05-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-02-03
  • 2019-05-03
相关资源
最近更新 更多