最近工作需要,写了如题的python脚本,只要安装了python3,即可使用。
Windows + python 3.9.6,64位
可以下载慢慢看:链接:https://pan.baidu.com/s/13nUjXeh7igx9Q3gGzYLVyg?pwd=1dkd
提取码:1dkd
递归遍历指定文件夹下所有图片(支持多层级文件夹),转为base64,存入指定文件夹下的txt文件中。
完整代码如下,粘贴到编辑器即可使用,代码最下方有示例:
# -*- coding: utf-8 -*-
import base64
import datetime
import math
import os
"""
遍历指定目录下的所有图片,存储 “filename,图片base64码”至txt文件。如“1.jpg,base64字符串”
文件名从1.txt开始,依次递增
参数:
img_root:图片文件夹路径。注意:末尾不加斜杠。例:C:\zhangyue1\桌面\测试数据\人像
batch:每个文件存放的数据行数,超出则创建新的txt文件继续写入
txt_root:存放txt文件的目录,如无,则自动创建该目录
"""
# 图片转base64
def img2base64(img_path_str):
"""图片转base64并返回str
:param img_path_str: 图片完整路径str,如r"C:\zhangyue1\桌面\测试数据\人像\1.jpg"
:return: 返回转码后的base64字符串
"""
with open(img_path_str, 'rb') as f:
img_path_str = f.read()
image_base64 = str(base64.b64encode(img_path_str), encoding='utf-8')
return image_base64
# 将str数据data追加存入文件file_path中。
def save_data(file_path: str, data: str):
"""将str数据data追加存入文件file_path中。
:param file_path: 文件完整路径。如“D:/test/1.txt”
:param data: 数据字符串
:return: 无返回值
"""
# mode='a',追加模式:不清空文档已有数据,每次在文档末尾追加data
with open(file=file_path, mode='a', encoding="utf-8") as file:
file.write(data)
# 遍历文件夹img_root中所有图片,转base64,逐行写到txt_root文件夹中的txt文件中,可设置每个txt文件写入个数(每个base64为1行)
def find_all_img_2_txt(img_root: str, txt_root: str, batch: int = 32):
"""
:param img_root: (必填)str,图片根目录
:param txt_root: (非必填)txt文件存放位置。
空,自动在img_root下创建文件夹“img_base64_txt”;
非空但不存在,自动创建该目录。
:param batch: 每个文件存储的图片数据个数(1个图存1行)。
默认为0,全部存入1.txt;
1-n,每个文件存batch条
:return: (str) result/error,成功后统计信息/错误提示
"""
''' 一、初始化 '''
# 记录运行开始时间
start_time = datetime.datetime.now()
# 已写入文件的图片总数量。初始为0-未写入
image_number = 0
# 图片存入的txt文件名称序号,初始为0-未写入
txt_name = 0
# 判断:img_root是否存在。不存在,print错误提示并返回
if img_root is None or img_root == "" or not os.path.exists(img_root):
error = f"图片路径\"{img_root}\"不存在"
print(error)
return error
# 判断:txt_root为空。默认在img_root下创建名为“img_base64_txt”的文件夹
if txt_root is None or txt_root == "":
txt_root = os.path.join(img_root, "img_base64_txt")
os.makedirs(txt_root)
# 判断:txt_root是否存在。不存在,创建该目录
if not os.path.exists(txt_root):
os.makedirs(txt_root)
''' 二、执行 '''
# 3种情况:
# 1、batch==0,全部存到1.txt中
if batch == 0:
# 1-1.写入文件的序号固定为1
txt_name = 1
# 1-2.拼文件存储path。使用变量txt_name替换"{txt_name}"
data_path = str(os.path.join(txt_root, f"{txt_name}.txt"))
# 1-3.递归遍历图片路径(os.walk(path):按照目录层级path,逐层遍历所有文件夹dirs、文件files。path下包含:dirs列表+files列表)
all_in_img_root = os.walk(img_root)
# 1-4.遍历所有文件
for path, dirs, files in all_in_img_root:
for filename in files:
# 1-4-1.找jpg文件。判断:文件名后缀是否“.jpg”。是,说明是图片,处理;否,不是图片,遍历下一个。
if filename.endswith(".jpg"):
# ① 图片计数+1
image_number += 1
# ② 图片转base64
img_base64_str = img2base64(os.path.join(path, filename))
# ③ base64写入1.txt:第1条数据,开头不用换行;以后每条数据,换行+数据字符串
if image_number == 1:
save_data(data_path, img_base64_str)
else:
save_data(data_path, "\n" + img_base64_str)
# 1-5.遍历完成后,判断:写入图片数量。0-没有,print提示
if image_number == 0:
error = f"文件夹\"{img_root}\"中,没有图片。"
print(error)
return error
# 2、batch>0,根据已写入图片数量,判断是否要写入新的txt文件
elif batch > 0:
# 2-1.递归遍历图片路径
all_in_img_root = os.walk(img_root)
# 2-2.遍历当前所有文件
for path, dirs, files in all_in_img_root:
for filename in files:
# 2-2-1.找jpg文件。判断:文件名后缀是否“.jpg”。是,说明是图片,处理;否,不是图片,遍历下一个。
if filename.endswith(".jpg"):
# ① 图片计数+1
image_number += 1
# ② 图片转base64
img_base64_str = img2base64(os.path.join(path, filename))
# ③ 判断:image_number除以batch的余数
# 余数=1:txt_name自增,开头不换行
if image_number % batch == 1:
txt_name += 1
# 拼文件存储path。使用变量txt_name替换"{txt_name}"
data_path = str(os.path.join(txt_root, f"{txt_name}.txt"))
save_data(data_path, img_base64_str)
# 余数!=1:txt_name不自增,开头换行
if image_number % batch != 1:
# 拼文件存储path。使用变量txt_name替换"{txt_name}"
data_path = str(os.path.join(txt_root, f"{txt_name}.txt"))
save_data(data_path, "\n" + img_base64_str)
# 1-5.遍历完成后,判断:写入图片数量。0-没有,print提示
if image_number == 0:
error = f"文件夹\"{img_root}\"中,没有图片。"
print(error)
return error
# 3、batch为其他-异常,print错误提示
else:
error = f"batch参数:{batch},错误!请输入大于等于0的整数。"
print(error)
return error
''' 成功结束后统计 '''
# 记录运行结束时间
end_time = datetime.datetime.now()
#
latency = end_time - start_time
result = r"目标:遍历图片 + 转base64 + 存入txt文件。已完成!" + "\n\n" + \
r"============ 结果统计 ============" + "\n" + \
f"转存图片数量:{image_number}" + "\n" + \
f"txt文件数量:{txt_name}" + "\n" + \
f"最大序号txt文件名:{txt_name}.txt" + "\n" + \
f"txt文件容量最大值:{batch}" + "\n" + \
f"图片根目录:{img_root}" + "\n" + \
f"txt文件位置:{txt_root}" + "\n" + \
f"总耗时:{latency}" + "\n" + \
r"============ 结果统计 ============"
print(result)
return result
if __name__ == '__main__':
# 图片根目录
img_root_str = r"D:\image"
# 文件存储根目录
txt_root_str = r"D:\list"
find_all_img_2_txt(img_root=img_root_str, txt_root=txt_root_str, batch=10)