2017-07-07 56 views
1

我正在嘗試向圖像添加第4個「頻道」。具體來說,我有一個RGB圖像,並希望將Canny濾波器找到的邊緣檢測圖像添加到該圖像矩陣中,然後將其用作神經網絡的輸入。向圖像添加新頻道

我有邊緣檢測工作,我甚至可以追加圖像,但由於某種原因,循環後數據'恢復'。我對圖像大小所做的更改不會保留。


代碼

我有三套32x32x3彩色圖像:X_trainX_validX_test。對於每一個,我正常化圖像,然後添加漸變。追加似乎在循環時產生影響,但循環後變更不存在。

代碼片斷

import cv2 as cv 
example_record = 2 

print('X_train is shape {}'.format(X_train.shape)) 
print('X_valid is shape {}'.format(X_valid.shape)) 
print('X_test is shape {}'.format(X_test.shape)) 

# Show before 
plt.imshow(X_valid[example_record]) 
plt.title('Validation Input {} Before Normalization'.format(example_record)) 

# Normalize 
canny_low = 50 
canny_high = 100 
for dataset in [X_train, X_valid, X_test]: 
    for i, img in enumerate(dataset): 
     cv.normalize(img, img, 0, 255, cv.NORM_MINMAX) 
     edges = cv.Canny(img, canny_low, canny_high) 
     edges = np.reshape(edges, (img.shape[0], img.shape[1], 1)) 
     img = np.concatenate((img, edges),axis=2) 
     if i == 0: 
      print('img shape after concatenation {}'.format(img.shape)) 

# Show after 
plt.figure() 
print('Updated image shape: {}'.format(X_valid[example_record].shape)) 
plt.imshow(X_valid[example_record]) 
plt.title('Validation Input {} After Normalization'.format(example_record)) 

輸出

X_train is shape (34799, 32, 32, 3) 
X_valid is shape (4410, 32, 32, 3) 
X_test is shape (12630, 32, 32, 3) 
img shape after concatenation (32, 32, 4) 
img shape after concatenation (32, 32, 4) 
img shape after concatenation (32, 32, 4) 
Updated image shape: (32, 32, 3) 

其他企圖

如果我更換img = np.concatenate((img, edges),axis=2)dataset[i] = np.concatenate((img, edges),axis=2),我得到的錯誤:

 21   edges = cv.Canny(img, canny_low, canny_high) 
    22   edges = np.reshape(edges, (img.shape[0], img.shape[1], 1)) 
---> 23   dataset[i] = np.concatenate((img, edges),axis=2) 
    24   if i == 0: 
    25    print('img shape after concatenation {}'.format(img.shape)) 

ValueError: could not broadcast input array from shape (32,32,4) into shape (32,32,3) 
+1

我強烈建議將img寫入新列表。 –

回答

1

好的,我以前的回答不夠詳細,不適合某人的口味,並且它被低估了。所以,讓我提供「現成」的解決方案:

# Normalize 
canny_low = 50 
canny_high = 100 
X = [X_train, X_valid, X_test] 
X_new = [np.empty(x.shape[:-1] + (x.shape[-1] + 1,), dtype=x.dtype) for x in X] 

for dataset, dsnew in zip(X, X_new): 
    for i, img in enumerate(dataset): 
     cv.normalize(img, img, 0, 255, cv.NORM_MINMAX) 
     edges = np.expand_dims(cv.Canny(img, canny_low, canny_high), axis=2) 
     dsnew[i, :, :, :] = np.concatenate((img, edges), axis=2) 

或者,你可以展開循環開始X_trainX_validX_test之前這可能會節省一些內存。

+0

@LonGonk爲您工作? –

+0

是的!我嘗試了這種方法,並且通過擴展數據集本身,並且都運行良好。我被卡住了,認爲'img'是一個參考而不是副本。 –

0
  1. 您內環

    for i, img in enumerate(dataset): 
    

    被覆蓋的級聯img

  2. print('X_train is shape {}'.format(X_train.shape)) 
    print('X_valid is shape {}'.format(X_train.shape)) 
    print('X_test is shape {}'.format(X_train.shape)) 
    

    正在打印X_train.shape的形狀值!

  3. IMG = np.concatenate(...)

    內環路後,你有什麼用連接的映像img嗎?你不覺得你必須以某種方式存儲結果,讓程序「記住」它嗎?

你的第二次嘗試是有希望的,只是不要在dataset存儲新img。在循環外定義一個dataset_new(創建一個空列表或正確形狀的numpy數組),然後在循環中執行dataset_new[i] = np.concatenate...

+0

這個答案的確觸及了這個問題,但不是解決方案。你應該添加更多。 –