gpt4 book ai didi

python - 在 tensorflow 中展开张量

转载 作者:行者123 更新时间:2023-12-04 00:51:30 25 4
gpt4 key购买 nike

在 TensorFlow 中,我打算用 sin(x) 的泰勒级数和某些近似项来操纵张量。为此,我尝试使用 sin(x) 的泰勒级数来处理灰度图像((32,32) 的形状)并且效果很好。现在,我无法将适用于形状为 (32,32) 的灰度图像的相同内容操作为形状为 (32,32,3) 的 RGB 图像>,它没有给我正确的数组。直觉上,我试图用 sin(x) 的泰勒展开来操纵张量。谁能告诉我在 tensorflow 中这样做的可能方法?有什么想法吗?

我的尝试:

这里是 sin(x)x=0 处的泰勒展开式:1- x + x**2/2 - x**3/6 有三个扩展项。

from tensorflow.keras.datasets import mnist
(X_train, y_train), (X_test, y_test) = mnist.load_data()

x= X_train[1,:,:,1]
k= 3
func = 'sin(x)'

new_x = np.zeros((x.shape[0], x.shape[1]*k))
new_x = new_x.astype('float32')
nn = 0
for i in range(x.shape[1]):
col_d = x[:,i].ravel()
new_x[:,nn] = col_d
if n_terms > 0:
for j in range(1,k):
if func == 'cos(x)':
new_x[:,nn+j] = new_x[:,nn+j-1]

我认为我可以使用 TensorFlow 更高效地完成此操作,但对我来说如何操作并不是很直观。任何人都可以建议一个可能的解决方法来完成这项工作吗?有什么想法吗?

更新:

在 2dim 数组中 col_d = x[:,i].ravel() 是将 2 dim 数组展平的像素向量。同样,我们可以通过这种方式将 3dim 数组 reshape 为 2dim:x.transpose(0,1,2).reshape(x.shape[1],-1) 在 for 循环中,所以它可能是 x[:,i].transpose(0,1,2).reshape(x.shape[1],-1),但这仍然不正确。我认为 tensorflow 可能有更好的方法来做到这一点。我们怎样才能更有效地用 sin(x) 的泰勒级数来操纵张量?有什么想法吗?

目标:

直观上,sin(x)的泰勒级数中,x是张量,如果我们只想要sin的泰勒级数的2、3个近似项(x) 对于每个张量,我想将它们连接成新的张量。我们应该如何在 TensorFlow 中高效地做到这一点?有什么想法吗?

最佳答案

new_x = np.zeros((x.shape[0], x.shape[1]*n_terms))

这行没有意义,为什么要为 3 个泰勒展开项分配 96 个元素的空间。

(new_x[:, 3:] == 0.0).all() = True # check

对于具有 n 项的像素级泰勒展开


def sin_exp_step(x, i):

c1 = 2 * i + 1
c2 = (-1) ** i / np.math.factorial(c1)

t = c2 * (x ** c1)

return t

# validate

x = 45.0
x = (np.pi / 180.0) * x

y = np.sin(x)

approx_y = 0

for i in range(n_terms):

approx_y += sin_exp_step(x, i)

abs(approx_y - y) < 1e-8

x= X_train[1,:,:,:]
n_terms = 3
func = 'sin(x)'

new_x = np.zeros((*x.shape, n_terms))

for i in range(0, n_terms):

if func == 'sin(x)': # sin(x)

new_x[..., i] += sin_exp_step(x, i)

避免使用通常的数值近似方法,因为它们计算量大(阶乘)且稳定性较差,因此对于高阶导数算法,例如,基于梯度的优化通常是最好的BFGSLBFGS 用于近似 hessian 矩阵(二阶导数)。 Adam 和 SGD 等优化器就足够了,而且计算消耗要少得多。使用神经网络,我们也许能够找到更好的扩展。


n-terms 扩展的 Tensorflow 解决方案

import numpy as np

import tensorflow as tf
from tensorflow.keras.datasets import cifar10
from tensorflow.keras.layers import Input, LocallyConnected2D
from tensorflow.keras.models import Model
from tensorflow.keras import backend as K

(x_train, y_train), (x_test, y_test) = cifar10.load_data()

x_train = tf.constant(x_train, dtype=tf.float32)
x_test = tf.constant(x_test, dtype=tf.float32)

def expansion_approx_of(func):

def reconstruction_loss(y_true, y_pred):

loss = (y_pred - func(y_true)) ** 2
loss = 0.5 * K.mean(loss)

return loss

return reconstruction_loss

class Expansion2D(LocallyConnected2D): # n-terms expansion layer

def __init__(self, i_shape, n_terms, kernel_size=(1, 1), *args, **kwargs):

if len(i_shape) != 3:

raise ValueError('...')

self.i_shape = i_shape
self.n_terms = n_terms

filters = self.n_terms * self.i_shape[-1]

super(Expansion2D, self).__init__(filters=filters, kernel_size=kernel_size,
use_bias=False, *args, **kwargs)

def call(self, inputs):

shape = (-1, self.i_shape[0], self.i_shape[1], self.i_shape[-1], self.n_terms)

out = super().call(inputs)

expansion = tf.reshape(out, shape)

out = tf.math.reduce_sum(expansion, axis=-1)

return out, expansion

inputs = Input(shape=(32, 32, 3))

# expansion: might be a taylor expansion or something better.
out, expansion = Expansion2D(i_shape=(32, 32, 3), n_terms=3)(inputs)

model = Model(inputs, [out, expansion])

opt = tf.keras.optimizers.Adam(learning_rate=0.0001, beta_1=0.9, beta_2=0.999)
loss = expansion_approx_of(K.sin)

model.compile(optimizer=opt, loss=[loss])

model.summary()

model.fit(x_train, x_train, batch_size=1563, epochs=100)

x_pred, x_exp = model.predict_on_batch(x_test[:32])

print((x_exp[0].sum(axis=-1) == x_pred[0]).all())

err = abs(x_pred - np.sin(x_test[0])).mean()

print(err)

关于python - 在 tensorflow 中展开张量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66131264/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com