paddle ocr

paddle ocr

paddle ocr笔记

准备工作

  1. 下载字典ppocr_keys_v1.txt,下标从1开始
  2. 模型转换

reference

to onnx

下载模型,或者直接使用python跑一下并且把本地模型拿过来用,一共三个模型:文本检测,文本方向校准,文字识别模型

复制代码
paddle2onnx --model_dir ./det/ch/ch_PP-OCRv4_det_infer --model_filename inference.pdmodel  --params_filename inference.pdiparams  --save_file ./det-model.onnx  --opset_version 11  --enable_onnx_checker True

paddle2onnx --model_dir ./rec/ch/ch_PP-OCRv4_rec_infer --model_filename inference.pdmodel  --params_filename inference.pdiparams  --save_file ./rec-model.onnx  --opset_version 11  --enable_onnx_checker True

paddle2onnx --model_dir ./cls/ch_ppocr_mobile_v2.0_cls_infer --model_filename inference.pdmodel  --params_filename inference.pdiparams  --save_file ./cls-padmodel.onnx  --opset_version 11  --enable_onnx_checker True

文本检测

复制代码
import onnxruntime
import cv2
import numpy as np

# 读取图片
# image = cv2.imread("chinese.png")
image = cv2.imread("none.png")

# 加载 ONNX 文本检测模型
det_session = onnxruntime.InferenceSession("./onnx/det-model.onnx")

# 预处理
det_input = cv2.resize(image, (640, 640)) / 255.0  # 归一化
det_input = np.transpose(det_input, (2, 0, 1))[np.newaxis, :, :, :].astype(np.float32)

# 推理
input_name = det_session.get_inputs()[0].name
output_name = det_session.get_outputs()[0].name
det_output = det_session.run([output_name], {input_name: det_input})[0]

# 获取非零值的索引(文本区域)
non_zero_indices = np.nonzero(det_output)

print(f'--------------------------')
print(f'len:{len(non_zero_indices[0])}')
# 打印非零值的索引及对应的值
for i in range(len(non_zero_indices[0])):
    print(f'--------------------------')
    coords = tuple(non_zero_indices[j][i] for j in range(len(non_zero_indices)))
    print(f"坐标: {coords}, 值: {det_output[coords]}")

文本检测

复制代码
import onnxruntime
import cv2
import numpy as np

# 读取图片
# image = cv2.imread("chinese.png")
# image = cv2.imread("none.png")
image = cv2.imread("oneline.png")

# 加载 ONNX 文本检测模型
det_session = onnxruntime.InferenceSession("./onnx/det-model.onnx")

# 预处理
det_input = cv2.resize(image, (640, 640)) / 255.0  # 归一化
# det_input = image / 255.0  # 归一化
det_input = np.transpose(det_input, (2, 0, 1))[np.newaxis, :, :, :].astype(np.float32)

# 推理
input_name = det_session.get_inputs()[0].name
output_name = det_session.get_outputs()[0].name
det_output = det_session.run([output_name], {input_name: det_input})[0]



#
#
#
# 获取非零值的索引(文本区域)
# non_zero_indices = np.nonzero(det_output)

# print(f'--------------------------')
# print(f'len:{len(non_zero_indices[0])}')
# # 打印非零值的索引及对应的值
# for i in range(len(non_zero_indices[0])):
#     print(f'--------------------------')
#     coords = tuple(non_zero_indices[j][i] for j in range(len(non_zero_indices)))
#     print(f"坐标: {coords}, 值: {det_output[coords]}")

# 5. 确保 `det_output` 是 4D (batch, channels, height, width)
print("det_output shape:", det_output.shape)

# 6. 获取二值化文本区域
box_thresh = 0.3
text_mask = (det_output[0, 0, :, :] > box_thresh).astype(np.uint8) * 255

# 7. 确保 `text_mask` 是单通道 2D 图像
print("text_mask shape:", text_mask.shape)  # 应该是 (height, width)

# 8. 显示二值化结果(可选)
cv2.imshow("Text Mask", text_mask)
cv2.waitKey(0)
cv2.destroyAllWindows()

# 9. 确保 `text_mask` 兼容 OpenCV
if len(text_mask.shape) == 3:
    text_mask = cv2.cvtColor(text_mask, cv2.COLOR_BGR2GRAY)

# 10. 轮廓检测
contours, _ = cv2.findContours(text_mask, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

# 11. 打印检测到的文本框
for contour in contours:
    x, y, w, h = cv2.boundingRect(contour)
    print(f"检测到的文本框: x={x}, y={y}, w={w}, h={h}")

文字识别

复制代码
import onnxruntime
import cv2
import numpy as np

# 读取图片
image = cv2.imread("rec-cv2.imread.png")

target_height = 48
h, w = image.shape[:2]
new_w = int(w * (target_height / h))
new_w = max(32, (new_w // 32) * 32)
image = cv2.resize(image, (new_w, target_height));
print(f'resize: {image.shape}')

# image = cv2.imread("none.png")

# 加载 ONNX 文本检测模型
rec_session = onnxruntime.InferenceSession("./onnx/rec-model.onnx")

# 预处理
# rec_input = cv2.resize(image, (640, 640)) / 255.0  # 归一化
rec_input = image / 255.0  # 归一化
rec_input = np.transpose(rec_input, (2, 0, 1))[np.newaxis, :, :, :].astype(np.float32)

print(f'shape: {rec_input.shape}')

# 推理
input_name = rec_session.get_inputs()[0].name
output_name = rec_session.get_outputs()[0].name
print(f'input_name: {input_name}')
print(f'output_name: {output_name}')
rec_output = rec_session.run([output_name], {input_name: rec_input})[0]

with open('onnx/dict.txt', 'r', encoding='utf-8') as f:
    dict_list = f.readlines()
    dict_list = [line.strip() for line in dict_list]
    # 返回下标的字典
    dict_index = {i + 1: char for i, char in enumerate(dict_list)}

print(rec_output[0].shape)


# 假设 rec_output[0] 的 shape 为 (60, 6625)
probabilities = rec_output[0]  # 取出 (60, 6625)

# Step 1: 找到每个时间步概率最高的索引
max_indices = np.argmax(probabilities, axis=1)  # shape: (60,)

# print(f'--dict: {dict_index}')
# Step 2: CTC 处理(去重)
decoded_text = []
prev_index = -1  # 记录前一个索引,避免重复
for index in max_indices:
    if index != prev_index and index in dict_index:  # 避免重复 & 确保索引合法
        print(f'--index: {index}, dict[{index}] = dict_index[{index}]')
        decoded_text.append(dict_index[index])
    prev_index = index

# Step 3: 转换为字符串
decoded_text = "".join(decoded_text)

print("识别结果:", decoded_text)
相关推荐
开开心心就好1 小时前
Word双击预览图片插件弥补Word功能缺失
人工智能·python·智能手机·ocr·电脑·word·音视频
蓝创工坊Blue Foundry3 小时前
扫描件批量转 Excel:先确认要整表还原还是字段汇总
python·pdf·ocr·excel
审小匠OpenCPAi1 天前
审计票据与财报 PDF 怎么识别?通用 OCR、表格结构识别与多模态大模型的精度对比
pdf·ocr·审计
小保CPP1 天前
OpenCV C++基于AI模型的场景文本识别(OCR)
c++·人工智能·opencv·计算机视觉·ocr
蓝创工坊Blue Foundry1 天前
批量提取图片中的数字:怎样整理成一张可核对的 Excel
python·ai·ocr·excel·paddlepaddle
求真学习2 天前
最新百度PaddleOCR开源HPD-Parsing,提出层级并行文档解析,1B模型解码步数最高压缩18倍,文档解析效率提升3倍!
百度·ocr·pdf解析·paddleocr·文档解析
Damon小智2 天前
眼见不一定为实:WAIC 2026 探展合合信息,实测 AI 去反光 + AI 跨模态鉴伪两项黑科技
人工智能·ocr
山石满棠2 天前
基于python313环境构建paddle-ocr镜像
ocr·paddle
AI人工智能+2 天前
药品经营许可证识别技术,融合计算机视觉、自然语言处理和知识图谱,保障药品供应链安全,助力构建智慧药监体系。
深度学习·ocr·药品经营许可证识别
蓝创工坊Blue Foundry2 天前
多个同模板 PDF,怎样批量提取同一类字段到 Excel
运维·数据库·pdf·自动化·ocr·excel