→
清理空值 防止出现cannot identify image file
#%pip install -i https://pypi.tuna.tsinghua.edu.cn/simple opencv-python
#可能需要重启jupyter
import os
import warnings
from PIL import Image
warnings.filterwarnings("error", category=UserWarning)
PATH = "data" #文件路径
i = 0
def is_read_successfully(file):
try:
imgFile = Image.open(file)
return True
except Exception:
return False
if __name__=="__main__":
#子文件夹
for childPATH in os.listdir(PATH):
#子文件夹路径
childPATH = PATH + '/'+ str(childPATH)
for parent, dirs, files in os.walk(PATH):
for file in files:
if not is_read_successfully(os.path.join(parent, file)):
print(os.path.join(parent, file))
i = i + 1
os.remove(os.path.join(parent, file))
print(i)
print(i)
# In[]删除子文件夹超过4000张的图
import os
def count_images_in_folder(folder_path):
image_count = 0
for file in os.listdir(folder_path):
if file.endswith('.jpg') or file.endswith('.png'):
image_count += 1
return image_count
def delete_images_above_limit(folder_path):
for file in os.listdir(folder_path):
if count_images_in_folder(folder_path) > 4000:
if file.endswith('.jpg') or file.endswith('.png'):
os.remove(os.path.join(folder_path, file))
def main():
mother_folder_path = 'data/'
i=0
for folder in os.listdir(mother_folder_path):
folder_path = os.path.join(mother_folder_path, folder)
if os.path.isdir(folder_path):
delete_images_above_limit(folder_path)
if __name__ == '__main__':
main()
# %%
重置大小 参考python批量修改图片尺寸(含多个文件夹)_python 修改路径下多个子文件下图片尺寸并重新保存-CSDN博客
# -*- coding: utf-8 -*-
import cv2
import matplotlib.pyplot as plt
import os
import re
import sys
from PIL import Image
import string
import numpy as np
PATH = "data/" #文件路径
i=0
pts=120
def resizeImage(file,NoResize):
image = cv2.imread(file,cv2.IMREAD_COLOR)
#如果type(image) == 'NoneType',会报错,导致程序中断,所以这里先跳过这些图片,
#并记录下来,结束程序后手动修改(删除)
if image is None:
NoResize += [str(file)]
else:
resizeImg = cv2.resize(image,(pts,pts))##若需要按比例,调用resize_img_keep_ratio(file,(pts,pts))
cv2.imwrite(file,resizeImg)
# cv2.waitKey(100)
def resizeAll(root):
global i
#待修改文件夹
fileList = os.listdir(root)
currentpath = os.getcwd()
os.chdir(root)
NoResize = [] #记录没被修改的图片
for file in fileList: #遍历文件夹中所有文件
i+=1
file = str(file)
resizeImage(file,NoResize)
os.chdir(currentpath) #改回程序运行前的工作目录
sys.stdin.flush() #刷新
print('未修改的图片: ',NoResize)
if __name__=="__main__":
#子文件夹
for childPATH in os.listdir(PATH):
#子文件夹路径
childPATH = PATH + '/'+ str(childPATH)
print(childPATH)
resizeAll(childPATH)
print(f'{i}张图片修改完成')
def resize_img_keep_ratio(img_name,target_size):
img = cv2.imread(img_name) # 读取图片
old_size= img.shape[0:2] # 原始图像大小
ratio = min(float(target_size[i])/(old_size[i]) for i in range(len(old_size))) # 计算原始图像宽高与目标图像大小的比例,并取其中的较小值
new_size = tuple([int(i*ratio) for i in old_size]) # 根据上边求得的比例计算在保持比例前提下得到的图像大小
img = cv2.resize(img,(new_size[1], new_size[0])) # 根据上边的大小进行放缩
pad_w = target_size[1] - new_size[1] # 计算需要填充的像素数目(图像的宽这一维度上)
pad_h = target_size[0] - new_size[0] # 计算需要填充的像素数目(图像的高这一维度上)
top,bottom = pad_h//2, pad_h-(pad_h//2)
left,right = pad_w//2, pad_w -(pad_w//2)
img_new = cv2.copyMakeBorder(img,top,bottom,left,right,cv2.BORDER_CONSTANT,None,(0,0,0))
return img_new
划分训练集测试集 参考【深度学习】使用python划分数据集为训练集和验证集和测试集并放在不同的文件夹_深度学习中有没有直接划分训练集、验证集和测试集的函数-CSDN博客
import os
import random
import shutil
from shutil import copy2
"""os.listdir会将文件夹下的文件名集合成一个列表并返回"""
def getDir(filepath):
pathlist=os.listdir(filepath)
return pathlist
"""制作五类图像总的训练集,验证集和测试集所需要的文件夹,例如训练集的文件夹中装有五个文件夹,这些文件夹分别装有一定比例的五类图像"""
def mkTotalDir(data_path):
os.makedirs(data_path)
dic=['train','test']
for i in range(0,2):
current_path=data_path+dic[i]+'/'
#这个函数用来判断当前路径是否存在,如果存在则创建失败,如果不存在则可以成功创建
isExists=os.path.exists(current_path)
if not isExists:
os.makedirs(current_path)
print('successful '+dic[i])
else:
print('is existed')
return
"""传入的参数是n类图像原本的路径,返回的是这个路径下各类图像的名称列表和图像的类别数"""
def getClassesMes(source_path):
classes_name_list=getDir(source_path)
classes_num=len(classes_name_list)
return classes_name_list,classes_num
"""change_path其实就是制作好的n类图像总的训练集,验证集和测试集的路径,sourcepath和上面一个函数相同
这个函数是用来建训练集,测试集,验证集下五类图像的文件夹,就是建15个文件夹,当然也可以建很多类
"""
def mkClassDir(source_path,change_path):
classes_name_list,classes_num=getClassesMes(source_path)
for i in range(0,classes_num):
current_class_path=os.path.join(change_path,classes_name_list[i])
isExists=os.path.exists(current_class_path)
if not isExists:
os.makedirs(current_class_path)
print('successful '+classes_name_list[i])
else:
print('is existed')
#source_path:原始多类图像的存放路径
#train_path:训练集图像的存放路径
#validation_path:验证集图像的存放路径D:\RSdata_dir\NWPU-RESISC45\\
#test_path:测试集图像的存放路径
def divideTrainValidationTest(source_path,train_path,test_path):
"""先获取五类图像的名称列表和类别数目"""
classes_name_list,classes_num=getClassesMes(source_path)
"""调用上面的函数,在训练集验证集和测试集文件夹下建立五类图像的文件夹"""
mkClassDir(source_path,train_path)
mkClassDir(source_path,test_path)
"""
先将一类图像的路径拿出来,将这个路径下所有这类的图片,就是800张图片的文件名做成一个列表,使用os.listdir函数,
然后再将列表里面的所有图像名进行shuffle就是随机打乱,然后从打乱后的图像中抽7成放入训练集,3成放入测试集的图像名称列表
"""
for i in range(0,classes_num):
source_image_dir=os.listdir(source_path+classes_name_list[i]+'/')
random.shuffle(source_image_dir)
train_image_list=source_image_dir[0:int(0.7*len(source_image_dir))]
test_image_list=source_image_dir[int(0.7*len(source_image_dir)):]
"""
找到每一个集合列表中每一张图像的原始图像位置,然后将这张图像复制到目标的路径下,一共是五类图像
每类图像随机被分成三个去向,使用shutil库中的copy2函数进行复制,当然也可以使用move函数,但是move
相当于移动图像,当操作结束后,原始文件夹中的图像会都跑到目标文件夹中,如果划分不正确你想重新划分
就需要备份,不然的话很麻烦
"""
for train_image in train_image_list:
origins_train_image_path=source_path+classes_name_list[i]+'/'+train_image
new_train_image_path=train_path+classes_name_list[i]+'/'
copy2(origins_train_image_path,new_train_image_path)
for test_image in test_image_list:
origins_test_image_path=source_path+classes_name_list[i]+'/'+test_image
new_test_image_path=test_path+classes_name_list[i]+'/'
copy2(origins_test_image_path,new_test_image_path)
if __name__=='__main__':
source_path = './data/'
data_path = './datadev/' #脚本新建的文件夹
train_path = './datadev/train/'
test_path = './datadev/test/'
mkTotalDir(data_path)
divideTrainValidationTest(source_path, train_path, test_path)