Reputation: 48916
I have a list called pairs
: pairs = []
Each item in the pairs
list is a pair of images:
pair = (im1,im2)
pairs.append(pair)
im1
and im2
are simply image files on the hard disk:
im1 = cv2.imread('im1.jpg')
im2 = cv2.imread('im2.jpg')
When I print the items in the pairs
list, I get a matrix representing the elements (images). How can I return the image file names (im1.jpg
and im2.jpg
) instead?
Thanks.
Upvotes: 1
Views: 1594
Reputation: 6180
The imread()
function of the opencv library returns a numpy array. So you can't really access the file name from this. I would try something like this:
class Image(object):
def __init__(self, image_name):
self.image_name = cv2.imread(image_name)
self.name = image_name
def __str__(self):
return self.name
Create your images:
im1 = Image('im1.jpg')
im2 = Image('im2.jpg')
Append the (im1, im2)
pair to your pairs
list. Then, when you print the the items in the pairs list just make sure to print their __str__
representation:
for p in pairs:
print (str(p[0]), str(p[1]))
Upvotes: 0
Reputation: 23012
You cannot get the filename from the array. The variable im1 = cv2.imread(...)
only stores the array values. It is stored as a standard numpy ndarray
object and there is no attribute referencing the filenames.
However, there are a lot of options here to do what you want, some that are very typical patterns for Python. Generally, you're looking to store two pieces of information: the filename and the image array. One option is just to have two lists, one being the filenames and the other the images:
>>> filename_list = ['im1.jpg', 'im2.jpg', ...]
>>> im_list = [cv2.imread(filename) for filename in filename_list]
Another way is to store these as pairs:
>>> filename1 = 'im1.jpg'
>>> filename2 = 'im2.jpg'
>>> im1 = cv2.imread(filename1)
>>> im2 = cv2.imread(filename2)
>>> im_pairs = [(filename1, im1), (filename2, im2), ...]
or if you already have the filenames and images as lists (as in the first case) you can use a list comprehension to build the pairs:
>>> im_pairs = [(filename, im) for filename, im in zip(filename_list, im_list)]
A better option (in terms of code reuse in actual projects) with the same idea as above is to create a namedtuple
so it's more explicit what each item is:
>>> from collections import namedtuple
>>> Img = namedtuple('Img', ['name', 'data'])
>>> im1 = Img('im1.jpg', np.array([5, 4, 3, 2, 1]))
>>> im1.name
'im1.jpg'
>>> im1.data
array([5, 4, 3, 2, 1])
And here you can just create a list of Img
objects.
A fourth option is to use a Python dictionary with the key being the name and the value being the arrays:
>>> filename1 = 'im1.jpg'
>>> filename2 = 'im2.jpg'
>>> im1 = cv2.imread(filename1)
>>> im2 = cv2.imread(filename2)
>>> im_pairs = {filename1: im1, filename2: im2, ...}
or again with a dictionary comprehension:
>>> im_pairs = {filename: im for filename, im in zip(filename_list, im_list)}
All of these methods are pretty standard so it's up to you how you'd want to use them. There are tons of other ways too, but I think the above are the most common.
Upvotes: 1