2017-02-07 4 views
0

Я создал список списков (каждая строка имеет 784 элементов) - это данные изображения 28x28 матрицаPython - не знаю, почему два списка смотрят одинаково (один обновляется в функции)

train_data, train_labels = X[:60000], Y[:60000] 

Для размытия изображений - вот две функции, которые вычисляют новое значение каждого пикселя - среднее значение, основанное на 8 соседних элементах в матрице 28x28 (игнорируется первая/последняя строка и первый/последний столбец для простоты, т. Е. Цикл от 2-26 вместо 0 -27)

def new_func(x_train_data,train_data): 
    for index in range(x_train_data.shape[0]): 
     imgvector = x_train_data[index].reshape(28, 28) 
     for iblur in range(2, 27): 
      for jblur in range(2, 27): 
       imgvector[iblur][jblur] = getNewVaueofPixel(imgvector, iblur, jblur) 
     print "blurring complete" 
     x_train_data[index] = imgvector.reshape(1, 784) 
     print np.array_equal(x_train_data[index], train_data) 

def getNewVaueofPixel(imgvector, iblur, jblur): 
    pixelval = 0.0 
    for ib in range(-1, 2): 
     for jb in range(-1, 2): 
      pixelval = pixelval + imgvector[iblur + ib][jblur + jb] 
    outval = round(pixelval/8.0, 12) 
    return ('{:.12f}'.format(outval)).rstrip('0') or 0. 

Вот вызов функции:

x_train_data = train_data[:1] 
x_train_labels = train_labels[0] 
new_func(x_train_data,train_data[0]) 

Ниже строки в функции возвращается true, но когда я смотрю на значение x_train_data [index], это не то же самое, что и оригинал, и оно было правильно обновлено.

print np.array_equal(x_train_data[index], train_data) 

Я потратил более 12 часов, отлаживая это, но не получая нигде. Просто не могу понять, почему train_data становится обновляется при

x_train_data = train_data[:1] 

необходимо создать копию списка, а не ссылку на него. Цените любую помощь.

+1

Если 'train_data' является' numpy.array', а не списком (списков), '[: 1]' создает 'view', а не копию. Возможно, вам придется прочитать основные массивы numpy (новые пользователи 'sckit-learn', похоже, вскакивают, не зная о« numpy », даже если набор построен на этом пакете.). Внутри вашей функции 'x_train_data' имеет атрибут' shape', как уверенный индикатор того, что это массив, а не список. – hpaulj

+0

Даже в обычном питоне использование [: 1] создаст [мелкую копию] (https://docs.python.org/3.4/library/copy.html). То есть, «Неглубокая копия создает новый составной объект, а затем (насколько это возможно) вставляет ссылки в него в объекты, найденные в оригинале». _ –

+0

благодарит @Fermiparadox и @hpaulj! Я думаю, мне нужно настроить новый массив нулей и обновить значения в нем. Будет читать на numpy.arrary. – hyperloopfan

ответ

0

Использование x_train_data = train_data[:1] создает view в numpy, так как @hpaulj сказал.

Например:

import numpy as np 

x = np.arange(5) 
y = x[:3] 

print(x) # [0 1 2 3 4] 
print(y) # [0 1 2] 

y[0] = 14 # This changes x as well 

print(x) # [14 1 2 3 4] 
print(y) # [14 1 2] 

Кроме того, в обычном питона было бы создать shallow copy.

x = [1, [2, 3]] 

y = x[:] 

print(x) # [1, [2, 3]] 
print(y) # [1, [2, 3]] 

y[1].append(7) # changes x as well 

print(x) # [1, [2, 3, 7]] 
print(y) # [1, [2, 3, 7]] 
Смежные вопросы