2

I am experiencing some bugs with this code that is supposed to write the info from an image into a csv file.

Currently I have this piece of code that writes all the pixels of the image [its X,Y coordinates to be exact] to a csv file.

import PIL
import numpy as np

img_grey = Image.open('walkingpath_005004.jpg').convert('L')
print(img_grey.size)
# (300, 241)
x = 3
y = 4
#pix = img_grey.load()
#print(pix[x,y])

# Taken from: https://stackoverflow.com/a/60783743/11089932
xy_coords = np.flip(np.column_stack(np.where(np.array(img_grey) >= 0)), axis=1)

# Add pixel numbers in front
pixel_numbers = np.expand_dims(np.arange(1, xy_coords.shape[0] + 1), axis=1)

#get rgb data
pixels = list(img_grey.getdata()) 
width, height = img_grey.size  
pixels = np.asarray(img_grey)

value = np.hstack([pixel_numbers, xy_coords, pixels])
print(value)
# [[    1     0     0]
#  [    2     1     0]
#  [    3     2     0]
#  ...
#  [72298   297   240]
#  [72299   298   240]
#  [72300   299   240]]

# Properly save as CSV
np.savetxt("outputdata.csv", value, delimiter='\t', fmt='%4d')

I need the RGB data of each pixel in 3 extra columns. As such, the format should be
PixelNumber X Y R G B

Currently faced with this bug: ValueError: all the input array dimensions for the concatenation axis must match exactly, but along dimension 0, the array at index 0 has size 258063 and the array at index 2 has size 509

I was looking at this link How to read the RGB value of a given pixel in Python?
but not sure how I can go about with incorporating it into my existing code.

Any and all help is appreciated!

Thank you!

Megan Darcy
  • 530
  • 5
  • 15

2 Answers2

3

The original solution for the xy_coords must be adapted since you're now dealing with three-channel images instead of single-channel images. And, to get the RGB tuples for each pixel, you just need to reshape the NumPy array, you already have.

from PIL import Image
import numpy as np

img = Image.open('path/to/your/image.png')
print('Inspect a few pixels in the original image:')
for y in np.arange(3):
    for x in np.arange(3):
        print(x, y, img.getpixel((x, y)))

# Modified for RGB images from: https://stackoverflow.com/a/60783743/11089932
img_np = np.array(img)
xy_coords = np.flip(np.column_stack(np.where(np.all(img_np >= 0, axis=2))), axis=1)
rgb = np.reshape(img_np, (np.prod(img_np.shape[:2]), 3))

# Add pixel numbers in front
pixel_numbers = np.expand_dims(np.arange(1, xy_coords.shape[0] + 1), axis=1)
value = np.hstack([pixel_numbers, xy_coords, rgb])
print('\nCompare pixels in result:')
for y in np.arange(3):
    for x in np.arange(3):
        print(value[(value[:, 1] == x) & (value[:, 2] == y)])

# Properly save as CSV
np.savetxt("outputdata.csv", value, delimiter='\t', fmt='%4d')

The two outputs for comparison:

Inspect a few pixels in the original image:
0 0 (63, 124, 239)
1 0 (65, 123, 239)
2 0 (64, 124, 240)
0 1 (74, 128, 238)
1 1 (66, 122, 239)
2 1 (68, 125, 239)
0 2 (173, 200, 244)
1 2 (86, 134, 239)
2 2 (80, 132, 240)

Compare pixels in result:
[[  1   0   0  63 124 239]]
[[  2   1   0  65 123 239]]
[[  3   2   0  64 124 240]]
[[301   0   1  74 128 238]]
[[302   1   1  66 122 239]]
[[303   2   1  68 125 239]]
[[601   0   2 173 200 244]]
[[602   1   2  86 134 239]]
[[603   2   2  80 132 240]]
----------------------------------------
System information
----------------------------------------
Platform:      Windows-10-10.0.19041-SP0
Python:        3.9.1
PyCharm:       2021.1.1
NumPy:         1.19.5
Pillow:        8.2.0
----------------------------------------
HansHirse
  • 18,010
  • 10
  • 38
  • 67
1

I think you could try with glob.glob, what should help from an exactly code perspective

import numpy as np
import glob
import cv2
import csv

image_list = []

for filename in glob.glob(r'C:\your path to\file*.png'):    # '*' will count files each by one
    
    #Read
    img = cv2.imread(filename)
    flattened = img.flatten() 
    print(flattened) # recommend to avoid duplicates, see files and so on.

    #Save
    with open('output2.csv', 'ab') as f: #ab is set 
            np.savetxt(f, flattened, delimiter=",")

Cheers



Also, find an easier method that is making fast and not weight image/csv

image_list = []
with open('train_train_.csv', 'w') as csv_file:
    csv_writer = csv.writer(csv_file, delimiter ='-')

    for filename in glob.glob(r'C:\your path to\file*.png'):

        img = cv2.imread(filename)
        image_list.append(img)
        csv_writer.writerow(img)
        print(img)
horizon
  • 67
  • 5