文件名 日期.pdf
Python 获得该文件保存到PDF文件夹,SQLite 中INSERT 该文件,并将日期.pdf 删除
PDF转图片进程 查询SQLite PDF表其中done为0 的那条数据,得到PDF地址 转换图片到图片库,文件名+时间戳.png 保存到IMG表。当全部转换完毕后设置该PDF表对应的数据键中的done为时间戳
OCR进程 查询img 表done为0 到 进行OCR 结果 json 保存到数据的info键 并将该条done为时间戳
文件名 日期.pdf
Python 获得该文件保存到PDF文件夹,SQLite 中INSERT 该文件,并将日期.pdf 删除
PDF转图片进程 查询SQLite PDF表其中done为0 的那条数据,得到PDF地址 转换图片到图片库,文件名+时间戳.png 保存到IMG表。当全部转换完毕后设置该PDF表对应的数据键中的done为时间戳
OCR进程 查询img 表done为0 到 进行OCR 结果 json 保存到数据的info键 并将该条done为时间戳
uploaded_file = st.file_uploader("选择一张图片", type=["png", "jpg", "jpeg"])
if uploaded_file is not None:
image = Image.open(uploaded_file)
st.image(image, caption="上传的图片", use_column_width=True)
save_path = os.path.join(UPLOAD_DIR, uploaded_file.name)
with open(save_path, "wb") as f:
f.write(uploaded_file.getbuffer())
st.success(f"图片已保存到:{save_path}")
import streamlit as st
from streamlit_pdf_viewer import pdf_viewer
st.header("Input info")
sx=st.text_input("TEXT")
user_age = st.slider("请选择您的年龄", 0, 100, 25)
tx=st.text_area("sqqqq")
btn_clicked = st.button("点击这里")
p=st.progress(0)
p.progress(user_age)
# 设置值
if btn_clicked:
st.write("mmmk",sx)
st.write("AGE",user_age)
st.write("Click")
st.write(p)
c=st.checkbox("同意吗")
st.write(c)
r=st.radio("选什么",{'axxxxxxx':"a",'bxxxx':"b",'c':"zzzzzzz"})
st.write("答案",r)
s=st.selectbox("选什么",['a',1,3,4,5])
st.write(s)
m=st.multiselect("选什么",['a',1,3,4,5])
st.write(m)
st.image("./a.jpg")
uploaded_file = st.file_uploader("选择一张图片", type=["png", "jpg", "jpeg"])
if uploaded_file is not None:
st.image(uploaded_file)
pv=st.file_uploader("上传PDF",type=['pdf'])
if pv is not None:
pdf_viewer(pv.read(),width=700,height=1000)
lst = ["苹果", "香蕉", "橙子"]
st.write(lst) # 默认 → ['苹果', '香蕉', '橙子']
st.code(lst, language="json") # 带灰底,更像代码块
st.markdown("\n".join(f"- {item}" for item in lst))
# //使用Markdown 实现显示列表进度
# 自由展示 columns
# 原始列表
fruit_list = [
{"name": "苹果", "price": 5.8, "pic": "apple"},
{"name": "香蕉", "price": 3.2, "pic": "banana"},
{"name": "橙子", "price": 4.5, "pic": "orange"},
]
# 用 columns 做“网格”:每行 3 张卡片
cols = st.columns(3)
for idx, fruit in enumerate(fruit_list):
col = cols[idx % 3] # 循环使用 3 列
with col:
# 卡片容器
with st.container(border=True):
# 1. 图(Unsplash 随机水果图)
img_url = f"https://source.unsplash.com/200x200/?fruit,{fruit['pic']}"
st.image(img_url, use_column_width=True)
# 2. 名称 + 价格
st.markdown(f"**{fruit['name']}**")
st.caption(f"¥{fruit['price']}/斤")
# 3. 数量选择
qty = st.number_input("斤数", min_value=0, max_value=20, step=1, key=f"qty_{idx}")
# 4. 折叠详情
with st.expander("查看详情"):
st.write("产地:南方优质果园")
st.write("甜度:★★★★☆")
# 5. 购买按钮
if st.button("加入购物车", key=f"buy_{idx}", type="primary"):
if qty == 0:
st.warning("请先选择数量!")
else:
st.success(f"已添加 {qty} 斤 {fruit['name']} 到购物车!")
1.能用8B 就用8B OCR下与2B 和 4B简直不是一个量级别,但是显存需求得12GB
2. qwen3vl 2B 的Q4 量化和qwen2.5vl 7b Q4 在OCR下情况差不多,但是qwen3vl 2B在prompt提示词语下可以做相对复杂的操作,比如总结归纳。
3. qwen3vl 2b 在Q4 (ollama 默认情况下的模型)量化下 300dpi的 A4 文件 无法识别较小的文字(5号字体以下),但是Q8 量化下 可以较好的识别出小字体。
4. qwen3VL 2b OCR整个文档会生成\n 换行符,会打断json格式输出,请在prompt中设置去除
prompt限制输出 以及惩罚
一、将文档中所有识别出的文字内容按阅读顺序拼接为一行字符串,彻底删除所有换行符(\n)、回车符(\r)、制表符(\t),仅保留单个空格作为字与字之间的分隔符 → 变量 all_raw
三、输出要求
若 all_raw 中仍包含 \n、\r、\t 或多行结构,视为格式错误,必须重新生成。