"OSError: 2" When converting TIFF image to PNG with Python Image Library
"OSError: 2" When converting TIFF image to PNG with Python Image Library
我创建了一个批处理作业,它可以打开文件夹中的 .TIFF 文件,调整它们的大小,将它们转换为 .PNG 文件,然后将它们保存在不同的文件夹中。批处理作业运行良好,图片得到正确处理,但在某些特定图片(我可以将其作为普通 .TIFF 文件打开)时,进程停止并显示以下错误日志:
---------------------------------------------------------------------------
OSError Traceback (most recent call last)
<ipython-input-3-499452368347> in <module>
47 target_size = (target_x, target_y)
48 print("Image gets converted from size " + str(img_size) + " to " + str(target_size))
---> 49 resized_image = image.resize(target_size, Image.BICUBIC)
50
51 # Save the image as a PNG to the target_dir
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\Image.py in resize(self, size, resample, box, reducing_gap)
1897
1898 if self.mode in ["LA", "RGBA"]:
-> 1899 im = self.convert(self.mode[:-1] + "a")
1900 im = im.resize(size, resample, box)
1901 return im.convert(self.mode)
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\Image.py in convert(self, mode, matrix, dither, palette, colors)
891 """
892
--> 893 self.load()
894
895 if not mode and self.mode == "P":
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\TiffImagePlugin.py in load(self)
1085 def load(self):
1086 if self.tile and self.use_load_libtiff:
-> 1087 return self._load_libtiff()
1088 return super().load()
1089
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\TiffImagePlugin.py in _load_libtiff(self)
1189
1190 if err < 0:
-> 1191 raise OSError(err)
1192
1193 return Image.Image.load(self)
OSError: -2
这个错误接缝真的不是不言自明的,我没有在网上找到合适的解决方案。有人可以帮忙吗?
这是完整的(相关)代码:
from PIL import Image
import os
# The directory which should be converted
source_dir = './Edge_Bands_Scan_Sorted/'
# The directory to which the converted files should be stored
target_dir = './Edge_Bands_Scan_Sorted_PNGs/'
# Create the target dir, if it does not exist already
if not os.path.exists(target_dir):
os.makedirs(target_dir)
count = 0
valid = 0
# Iterate through all the files in the source_dir-directory
for subdir, dirs, files in os.walk(source_dir):
for file in files:
# Check if file is a TIFF-File:
#if(file[-5:] == '.tiff' or file[-5:] == '.TIFF' ):
if file.lower().endswith(".tiff"):
file_path = os.path.join(subdir, file)
#Print list of all files
#print(file_path)
# Extract edge band pattern name from the filepath
# Get postion of last backslash and only get the text after this backslash
last_backslash_position = file_path.rfind("\")
after_last_backslash = file_path[last_backslash_position + 1:]
# Remove file ending
after_last_backslash_without_ending = after_last_backslash[:-5]
# Only the text before the first underscore is the REHAU Color Code
first_underscore_position = after_last_backslash_without_ending.find("_")
color_code = after_last_backslash_without_ending[:first_underscore_position]
# open the files to write
file = open(list_path, 'a')
error_file = open(error_list_path, 'a')
# Check if the colorcode is already converted
if not color_code in converted_color_codes_list:
try:
# Process the image
print("Loading image [{}] {}".format(count, file_path))
# Use PIl to load the image - there are problems with some images
image = Image.open(file_path)
# Get the image size
img_size = image.size
img_x = image.size[0]
img_y = image.size[1]
# Target width of the image
target_x = 1000
target_y = int(img_y * target_x / img_x)
target_size = (target_x, target_y)
print("Image [{}] gets converted from size {} to {} ".format( count, str(img_size), str(target_size)))
resized_image = image.resize(target_size, Image.BICUBIC)
# Save the image as a PNG to the target_dir
new_path = target_dir + color_code + '.png'
print("The converted image [{}] gets saved to path {}".format( count, new_path))
resized_image.save(new_path, "PNG", optimize=True, compress_level=6)
# If successful, add the color code to the list
# First add a new line
if existing_list:
file.write("\n")
# Then add the color code
file.write(color_code)
existing_list = True
valid += 1
except OSError:
print("ERROR: Image [{}] at path {} could not be processed".format (count, file_path))
# If there occurs an error while processing, save the image name and path to the file
if existing_error_list:
error_file.write("\n")
# Then add the color code
error_file.write(color_code + " - " + file_path)
existing_error_list = True
else:
#Handle duplicate files
print("DUPLICATE: Image [{}] at path {} with color code {} is already converted".format(count, file_path, color_code))
count += 1
# Close the file access again
error_file.close()
file.close()
else:
#Ignore other filetypes
break
print("{}/{} were successfully converted".format(valid, count))
该文件夹在嵌套子目录系统中包含大约 2100 张 .tiff 图像。其中 149 个未正确处理,但另一个处理良好。我看不出正确处理的图片和导致错误的图片有什么区别。
这是正确处理的图片路径示例:
./Edge_Bands_Scan_Sorted/Wooden\TIFF\W_E_B_NG75B_W_E_B_NG.TIFF
这是未正确处理的图片示例路径:./Edge_Bands_Scan_Sorted/Wooden\TIFF\W_E_B_NG00B_W_E_B_NG.TIFF
我不太确定这里发生了什么。我认为,但我绝不能确定,问题是文件每个像素有 4 个样本(即 RGBA),但 "Sample Format" 标签只给出类型(即无符号整数) 对于 4 个样本中的 3 个,这让图书馆感到不安。
这里是 tiffdump
输出,其中突出显示了相互矛盾的字段:
tiffdump 3200B_W_E_B_NG.TIFF
3200B_W_E_B_NG.TIFF:
Magic: 0x4949 <little-endian> Version: 0x2a <ClassicTIFF>
Directory 0: offset 9441002 (0x900eea) next 0 (0)
SubFileType (254) LONG (4) 1<0>
ImageWidth (256) LONG (4) 1<5477>
ImageLength (257) LONG (4) 1<1248>
BitsPerSample (258) SHORT (3) 4<8 8 8 8>
Compression (259) SHORT (3) 1<5>
Photometric (262) SHORT (3) 1<2>
StripOffsets (273) LONG (4) 1248<8 7558 15109 22684 30223 37769 45253 52740 60181 67699 75210 82702 90231 97784 105221 112698 120165 127581 135073 142615 150195 157794 165402 173003 ...>
Orientation (274) SHORT (3) 1<1>
SamplesPerPixel (277) SHORT (3) 1<4> <--- 4 SAMPLES PER PIXEL
RowsPerStrip (278) LONG (4) 1<1>
StripByteCounts (279) LONG (4) 1248<7550 7551 7575 7539 7546 7484 7487 7441 7518 7511 7492 7529 7553 7437 7477 7467 7416 7492 7542 7580 7599 7608 7601 7565 ...>
XResolution (282) RATIONAL (5) 1<1600>
YResolution (283) RATIONAL (5) 1<1600>
PlanarConfig (284) SHORT (3) 1<1>
ResolutionUnit (296) SHORT (3) 1<2>
Predictor (317) SHORT (3) 1<2>
ExtraSamples (338) SHORT (3) 1<2>
SampleFormat (339) SHORT (3) 3<1 1 1> <--- ONLY THREE FORMATS BUT 4 SAMPLES
作为解决方法,tifffile
似乎可以打开“不开心”图像,因此您可以使用:
from tifffile import imread
# Open with "tifffile"
img = imread('3200B_W_E_B_NG.TIFF')
# Make into "PIL Image" and carry on as usual
pi = Image.fromarray(img)
我创建了一个批处理作业,它可以打开文件夹中的 .TIFF 文件,调整它们的大小,将它们转换为 .PNG 文件,然后将它们保存在不同的文件夹中。批处理作业运行良好,图片得到正确处理,但在某些特定图片(我可以将其作为普通 .TIFF 文件打开)时,进程停止并显示以下错误日志:
---------------------------------------------------------------------------
OSError Traceback (most recent call last)
<ipython-input-3-499452368347> in <module>
47 target_size = (target_x, target_y)
48 print("Image gets converted from size " + str(img_size) + " to " + str(target_size))
---> 49 resized_image = image.resize(target_size, Image.BICUBIC)
50
51 # Save the image as a PNG to the target_dir
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\Image.py in resize(self, size, resample, box, reducing_gap)
1897
1898 if self.mode in ["LA", "RGBA"]:
-> 1899 im = self.convert(self.mode[:-1] + "a")
1900 im = im.resize(size, resample, box)
1901 return im.convert(self.mode)
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\Image.py in convert(self, mode, matrix, dither, palette, colors)
891 """
892
--> 893 self.load()
894
895 if not mode and self.mode == "P":
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\TiffImagePlugin.py in load(self)
1085 def load(self):
1086 if self.tile and self.use_load_libtiff:
-> 1087 return self._load_libtiff()
1088 return super().load()
1089
C:\EigeneProgramme\Python38-64\lib\site-packages\PIL\TiffImagePlugin.py in _load_libtiff(self)
1189
1190 if err < 0:
-> 1191 raise OSError(err)
1192
1193 return Image.Image.load(self)
OSError: -2
这个错误接缝真的不是不言自明的,我没有在网上找到合适的解决方案。有人可以帮忙吗?
这是完整的(相关)代码:
from PIL import Image
import os
# The directory which should be converted
source_dir = './Edge_Bands_Scan_Sorted/'
# The directory to which the converted files should be stored
target_dir = './Edge_Bands_Scan_Sorted_PNGs/'
# Create the target dir, if it does not exist already
if not os.path.exists(target_dir):
os.makedirs(target_dir)
count = 0
valid = 0
# Iterate through all the files in the source_dir-directory
for subdir, dirs, files in os.walk(source_dir):
for file in files:
# Check if file is a TIFF-File:
#if(file[-5:] == '.tiff' or file[-5:] == '.TIFF' ):
if file.lower().endswith(".tiff"):
file_path = os.path.join(subdir, file)
#Print list of all files
#print(file_path)
# Extract edge band pattern name from the filepath
# Get postion of last backslash and only get the text after this backslash
last_backslash_position = file_path.rfind("\")
after_last_backslash = file_path[last_backslash_position + 1:]
# Remove file ending
after_last_backslash_without_ending = after_last_backslash[:-5]
# Only the text before the first underscore is the REHAU Color Code
first_underscore_position = after_last_backslash_without_ending.find("_")
color_code = after_last_backslash_without_ending[:first_underscore_position]
# open the files to write
file = open(list_path, 'a')
error_file = open(error_list_path, 'a')
# Check if the colorcode is already converted
if not color_code in converted_color_codes_list:
try:
# Process the image
print("Loading image [{}] {}".format(count, file_path))
# Use PIl to load the image - there are problems with some images
image = Image.open(file_path)
# Get the image size
img_size = image.size
img_x = image.size[0]
img_y = image.size[1]
# Target width of the image
target_x = 1000
target_y = int(img_y * target_x / img_x)
target_size = (target_x, target_y)
print("Image [{}] gets converted from size {} to {} ".format( count, str(img_size), str(target_size)))
resized_image = image.resize(target_size, Image.BICUBIC)
# Save the image as a PNG to the target_dir
new_path = target_dir + color_code + '.png'
print("The converted image [{}] gets saved to path {}".format( count, new_path))
resized_image.save(new_path, "PNG", optimize=True, compress_level=6)
# If successful, add the color code to the list
# First add a new line
if existing_list:
file.write("\n")
# Then add the color code
file.write(color_code)
existing_list = True
valid += 1
except OSError:
print("ERROR: Image [{}] at path {} could not be processed".format (count, file_path))
# If there occurs an error while processing, save the image name and path to the file
if existing_error_list:
error_file.write("\n")
# Then add the color code
error_file.write(color_code + " - " + file_path)
existing_error_list = True
else:
#Handle duplicate files
print("DUPLICATE: Image [{}] at path {} with color code {} is already converted".format(count, file_path, color_code))
count += 1
# Close the file access again
error_file.close()
file.close()
else:
#Ignore other filetypes
break
print("{}/{} were successfully converted".format(valid, count))
该文件夹在嵌套子目录系统中包含大约 2100 张 .tiff 图像。其中 149 个未正确处理,但另一个处理良好。我看不出正确处理的图片和导致错误的图片有什么区别。
这是正确处理的图片路径示例:
./Edge_Bands_Scan_Sorted/Wooden\TIFF\W_E_B_NG75B_W_E_B_NG.TIFF
这是未正确处理的图片示例路径:./Edge_Bands_Scan_Sorted/Wooden\TIFF\W_E_B_NG00B_W_E_B_NG.TIFF
我不太确定这里发生了什么。我认为,但我绝不能确定,问题是文件每个像素有 4 个样本(即 RGBA),但 "Sample Format" 标签只给出类型(即无符号整数) 对于 4 个样本中的 3 个,这让图书馆感到不安。
这里是 tiffdump
输出,其中突出显示了相互矛盾的字段:
tiffdump 3200B_W_E_B_NG.TIFF
3200B_W_E_B_NG.TIFF:
Magic: 0x4949 <little-endian> Version: 0x2a <ClassicTIFF>
Directory 0: offset 9441002 (0x900eea) next 0 (0)
SubFileType (254) LONG (4) 1<0>
ImageWidth (256) LONG (4) 1<5477>
ImageLength (257) LONG (4) 1<1248>
BitsPerSample (258) SHORT (3) 4<8 8 8 8>
Compression (259) SHORT (3) 1<5>
Photometric (262) SHORT (3) 1<2>
StripOffsets (273) LONG (4) 1248<8 7558 15109 22684 30223 37769 45253 52740 60181 67699 75210 82702 90231 97784 105221 112698 120165 127581 135073 142615 150195 157794 165402 173003 ...>
Orientation (274) SHORT (3) 1<1>
SamplesPerPixel (277) SHORT (3) 1<4> <--- 4 SAMPLES PER PIXEL
RowsPerStrip (278) LONG (4) 1<1>
StripByteCounts (279) LONG (4) 1248<7550 7551 7575 7539 7546 7484 7487 7441 7518 7511 7492 7529 7553 7437 7477 7467 7416 7492 7542 7580 7599 7608 7601 7565 ...>
XResolution (282) RATIONAL (5) 1<1600>
YResolution (283) RATIONAL (5) 1<1600>
PlanarConfig (284) SHORT (3) 1<1>
ResolutionUnit (296) SHORT (3) 1<2>
Predictor (317) SHORT (3) 1<2>
ExtraSamples (338) SHORT (3) 1<2>
SampleFormat (339) SHORT (3) 3<1 1 1> <--- ONLY THREE FORMATS BUT 4 SAMPLES
作为解决方法,tifffile
似乎可以打开“不开心”图像,因此您可以使用:
from tifffile import imread
# Open with "tifffile"
img = imread('3200B_W_E_B_NG.TIFF')
# Make into "PIL Image" and carry on as usual
pi = Image.fromarray(img)