Cơ bảnHướng dẫnClaude APINguồn: Anthropic

OCR với Claude — Trích xuất text từ hình ảnh và tài liệu

Nghe bài viết
00:00

Điểm nổi bật

Nhấn để đến mục tương ứng

  1. 1 Tận dụng Claude hiệu quả: Tiêu chí Tesseract truyền thống Claude Vision Ảnh nghiêng, xoay Cần pre-process Xử lý được trực tiếp Font lạ, chữ tay — mẹo quan trọng là cung cấp đủ ngữ cảnh để AI trả về kết quả chính xác hơn 80% so với prompt chung chung.
  2. 2 Góc nhìn thực tế: import anthropic import base64 def ocrimageimagepath: str, language: str = "Vietnamese" -> str: """ Trich xuat toan. Điều quan trọng là hiểu rõ khi nào nên và không nên áp dụng phương pháp này.
  3. 3 Nội dung cốt lõi: "don thuoc", "bien ban hop", "nhat ky" """ with openimagepath, "rb" as f: data = base64.standardb64encodef.read.decode. Nắm vững phần này sẽ giúp bạn áp dụng hiệu quả hơn 70% so với đọc lướt toàn bài.
  4. 4 Tận dụng Claude hiệu quả: Tuy nhiên có một số lưu ý: def ocrvietnamesedocumentimagepath: str -> str: """OCR cho tai lieu tieng Viet.""" with — mẹo quan trọng là cung cấp đủ ngữ cảnh để AI trả về kết quả chính xác hơn 80% so với prompt chung chung.
  5. 5 Thành thật mà nói: Pre-process ảnh trước khi gửi from PIL import Image, ImageEnhance, ImageFilter def enhanceforocrimagepath: str ->. Phương pháp này hiệu quả trong hầu hết trường hợp, nhưng bạn cần điều chỉnh cho phù hợp ngữ cảnh riêng.
black and silver asus laptop computer

OCR (Optical Character Recognition) là bài toán cổ điển trong xử lý hình ảnh — nhận diện và trích xuất text từ ảnh. Các giải pháp OCR truyền thống như Tesseract hoạt động tốt với tài liệu in đều, nhưng gặp khó khăn với ảnh nghiêng, font chữ lạ, hoặc chữ viết tay.

Claude Vision thay đổi cuộc chơi: không chỉ đọc text mà còn hiểu context — biết đây là hóa đơn, danh thiếp, hay biên bản họp, và trả về thông tin theo cấu trúc phù hợp.

Tại sao Claude OCR tốt hơn Tesseract?

Tiêu chí Tesseract (truyền thống) Claude Vision
Ảnh nghiêng, xoay Cần pre-process Xử lý được trực tiếp
Font lạ, chữ tay Độ chính xác thấp Khá tốt
Tiếng Việt có dấu Cần cấu hình đặc biệt Native support
Hiểu cấu trúc tài liệu Không Có (bảng, form, hóa đơn)
Trả về JSON có structure Không, chỉ raw text Có thể yêu cầu
Chi phí Miễn phí, local Tính theo token
Tốc độ với batch lớn Nhanh hơn Chậm hơn, có rate limit

Kết luận: Dùng Tesseract cho batch lớn tài liệu in chuẩn. Dùng Claude khi cần độ chính xác cao với tài liệu phức tạp, hoặc khi cần structured output.

OCR cơ bản — Trích xuất raw text

import anthropic
import base64

def ocr_image(image_path: str, language: str = "Vietnamese") -> str:
    """
    Trich xuat toan bo van ban tu mot anh.

    Args:
        image_path: Duong dan den file anh
        language: Ngon ngu chinh trong anh

    Returns:
        Van ban duoc trich xuat
    """
    with open(image_path, "rb") as f:
        data = base64.standard_b64encode(f.read()).decode()

    # Xac dinh media type
    ext = image_path.lower().rsplit(".", 1)[-1]
    media_types = {
        "jpg": "image/jpeg", "jpeg": "image/jpeg",
        "png": "image/png", "gif": "image/gif", "webp": "image/webp"
    }
    media_type = media_types.get(ext, "image/jpeg")

    client = anthropic.Anthropic()
    message = client.messages.create(
        model="claude-haiku-4-5",
        max_tokens=4096,
        messages=[
            {
                "role": "user",
                "content": [
                    {
                        "type": "image",
                        "source": {"type": "base64", "media_type": media_type, "data": data}
                    },
                    {
                        "type": "text",
                        "text": f"""Trich xuat toan bo van ban trong hinh anh nay.
Ngon ngu chinh: {language}.

Huong dan:
- Giu nguyen dinh dang nguyen ban (xuat xuong dong, tab, khoang trang)
- Khong them nhan xet hay mo ta
- Neu co phan nao khong ro, danh dau [KHONG RO]
- Chi tra ve van ban, khong co gi them"""
                    }
                ]
            }
        ]
    )
    return message.content[0].text

OCR có cấu trúc — Trích xuất theo field

Đọc hóa đơn / receipt

def extract_receipt(image_path: str) -> dict:
    """Trich xuat thong tin tu hoa don mua sam."""
    with open(image_path, "rb") as f:
        data = base64.standard_b64encode(f.read()).decode()

    client = anthropic.Anthropic()
    message = client.messages.create(
        model="claude-haiku-4-5",
        max_tokens=2048,
        messages=[
            {
                "role": "user",
                "content": [
                    {
                        "type": "image",
                        "source": {"type": "base64", "media_type": "image/jpeg", "data": data}
                    },
                    {
                        "type": "text",
                        "text": """Trich xuat thong tin tu hoa don nay va tra ve JSON voi format sau:

{
  "store_name": "ten cua hang",
  "date": "ngay (DD/MM/YYYY)",
  "time": "gio (HH:MM)",
  "items": [
    {"name": "ten san pham", "quantity": so_luong, "unit_price": don_gia, "total": thanh_tien}
  ],
  "subtotal": tong_truoc_thue,
  "tax": tien_thue,
  "total": tong_cuoi,
  "payment_method": "hinh_thuc_thanh_toan",
  "cashier": "thu_ngan_neu_co"
}

Chi tra ve JSON, khong them gi khac."""
                    }
                ]
            }
        ]
    )

    import json
    try:
        return json.loads(message.content[0].text)
    except json.JSONDecodeError:
        return {"raw": message.content[0].text}

Đọc danh thiếp (business card)

def extract_business_card(image_path: str) -> dict:
    """Trich xuat thong tin lien lac tu danh thiec."""
    with open(image_path, "rb") as f:
        data = base64.standard_b64encode(f.read()).decode()

    client = anthropic.Anthropic()
    message = client.messages.create(
        model="claude-haiku-4-5",
        max_tokens=512,
        messages=[
            {
                "role": "user",
                "content": [
                    {
                        "type": "image",
                        "source": {"type": "base64", "media_type": "image/jpeg", "data": data}
                    },
                    {
                        "type": "text",
                        "text": """Trich xuat thong tin tu danh thiec nay, tra ve JSON:

{
  "name": "ho ten day du",
  "title": "chuc danh",
  "company": "ten cong ty",
  "email": "email hoac null",
  "phone": ["so dien thoai 1", "so 2 neu co"],
  "address": "dia chi hoac null",
  "website": "website hoac null",
  "social": {"linkedin": "...", "facebook": "..."}
}

Chi tra ve JSON."""
                    }
                ]
            }
        ]
    )

    import json
    try:
        return json.loads(message.content[0].text)
    except json.JSONDecodeError:
        return {"raw": message.content[0].text}

Xử lý chữ viết tay

Chữ viết tay là thách thức lớn với OCR truyền thống nhưng Claude xử lý khá tốt:

def transcribe_handwriting(
    image_path: str,
    context: str = ""
) -> str:
    """
    Chuyen chu viet tay thanh text.

    Args:
        image_path: Anh chua chu viet tay
        context: Nguyen canh (e.g. "don thuoc", "bien ban hop", "nhat ky")
    """
    with open(image_path, "rb") as f:
        data = base64.standard_b64encode(f.read()).decode()

    context_hint = f"Day la {context}. " if context else ""

    client = anthropic.Anthropic()
    message = client.messages.create(
        model="claude-opus-4-5",  # Dung Opus cho handwriting phuc tap
        max_tokens=4096,
        messages=[
            {
                "role": "user",
                "content": [
                    {
                        "type": "image",
                        "source": {"type": "base64", "media_type": "image/jpeg", "data": data}
                    },
                    {
                        "type": "text",
                        "text": f"""{context_hint}Hay doc va chuyen chu viet tay trong anh thanh van ban dang.

Luu y:
- Co gang doc chinh xac tung chu
- Giu nguyen cau truc doan van va xuong dong
- Neu mot tu khong ro, doan hop ly va danh dau voi [?]
- Dung doan moi khi co khoang trong lon trong anh
- Tra ve van ban thuan tuy"""
                    }
                ]
            }
        ]
    )
    return message.content[0].text

Tiếng Việt — Xử lý dấu thanh

Claude đọc tiếng Việt tốt hơn Tesseract đáng kể vì được train trên lượng lớn text Việt. Tuy nhiên có một số lưu ý:

def ocr_vietnamese_document(image_path: str) -> str:
    """OCR cho tai lieu tieng Viet."""
    with open(image_path, "rb") as f:
        data = base64.standard_b64encode(f.read()).decode()

    client = anthropic.Anthropic()
    message = client.messages.create(
        model="claude-haiku-4-5",
        max_tokens=4096,
        messages=[
            {
                "role": "user",
                "content": [
                    {
                        "type": "image",
                        "source": {"type": "base64", "media_type": "image/jpeg", "data": data}
                    },
                    {
                        "type": "text",
                        "text": """Day la tai lieu tieng Viet. Trich xuat toan bo noi dung.

Yeu cau quan trong:
- Giu nguyen dau thanh dieu (a, a, a, a, a, v.v.)
- Giu nguyen dac tu (d, d) va chu co dau mui ten (u, u, o, o, a, e)
- Neu font kho doc dan den sai dau, hay su dung nguyen canh de suy luan
- Khong thay the tieng Viet bang tieng Anh
- Tra ve van ban thuan tuy, giu nguyen dinh dang"""
                    }
                ]
            }
        ]
    )
    return message.content[0].text

Batch OCR — Xử lý nhiều trang

Khi cần OCR nhiều ảnh (ví dụ: tài liệu nhiều trang đã scan), xử lý tuần tự với rate limiting:

import time
from pathlib import Path

def batch_ocr(
    image_paths: list,
    output_dir: str = "ocr_output",
    delay: float = 0.5
) -> dict:
    """
    OCR nhieu anh, luu ket qua ra file.

    Args:
        image_paths: Danh sach duong dan anh
        output_dir: Thu muc luu ket qua
        delay: Delay giua cac request (giay)

    Returns:
        Dict {filename: extracted_text}
    """
    Path(output_dir).mkdir(exist_ok=True)
    results = {}

    for i, path in enumerate(image_paths):
        print(f"Dang xu ly {i+1}/{len(image_paths)}: {path}")

        try:
            text = ocr_image(path)
            results[path] = text

            # Luu ra file rieng
            out_path = Path(output_dir) / (Path(path).stem + ".txt")
            with open(out_path, "w", encoding="utf-8") as f:
                f.write(text)

        except Exception as e:
            print(f"Loi khi xu ly {path}: {e}")
            results[path] = f"ERROR: {e}"

        # Rate limiting
        if i < len(image_paths) - 1:
            time.sleep(delay)

    return results

Tips để tăng độ chính xác OCR

1. Pre-process ảnh trước khi gửi

from PIL import Image, ImageEnhance, ImageFilter

def enhance_for_ocr(image_path: str) -> bytes:
    """Tang chat luong anh truoc khi OCR."""
    with Image.open(image_path) as img:
        # Chuyen sang grayscale neu can
        if img.mode not in ("L", "RGB"):
            img = img.convert("RGB")

        # Tang contrast
        enhancer = ImageEnhance.Contrast(img)
        img = enhancer.enhance(2.0)

        # Tang do sac net
        img = img.filter(ImageFilter.SHARPEN)

        # Luu vao buffer
        import io
        buf = io.BytesIO()
        img.save(buf, format="JPEG", quality=95)
        return buf.getvalue()

2. Cung cấp context cho Claude

Luôn nói với Claude đây là loại tài liệu gì — điều này giúp nó suy luận đúng hơn khi gặp phần khó đọc:

# Thay vi
"Trich xuat van ban"

# Nen dung
"Day la hoa don VAT cua mot cua hang ban le. Trich xuat toan bo noi dung."

# Hoac
"Day la bien ban cuoc hop cua mot cong ty Viet Nam. Doc va chuyen chu viet tay thanh van ban."

3. Chia nhỏ tài liệu lớn

Với tài liệu nhiều thông tin, chia nhỏ câu hỏi thay vì hỏi tất cả một lúc:

def extract_invoice_in_parts(image_path: str) -> dict:
    """Trich xuat hoa don theo tung phan."""
    # Phan 1: Thong tin chung
    header = ask_about_image(image_path,
        "Chi trich xuat: so hoa don, ngay, ten ben ban, ten ben mua. JSON only.")

    # Phan 2: Line items
    items = ask_about_image(image_path,
        "Chi trich xuat danh sach san pham/dich vu voi gia. JSON array only.")

    # Phan 3: Tong ket
    totals = ask_about_image(image_path,
        "Chi trich xuat: tong tien, thue, tong cuoi, hinh thuc thanh toan. JSON only.")

    return {"header": header, "items": items, "totals": totals}

Khi nào Claude OCR không phù hợp?

  • Batch hàng nghìn trang — Chi phí cao, dùng Tesseract hoặc Google Document AI
  • Real-time OCR — Latency API không phù hợp cho ứng dụng scan liên tục
  • Tài liệu in đều, font chuẩn — Tesseract đủ tốt và miễn phí
  • Cần on-premise, không gửi data ra ngoài — Claude là cloud API

Tổng kết

Claude Vision là công cụ OCR mạnh mẽ khi bạn cần:

  • Đọc tài liệu phức tạp (ảnh nghiêng, font lạ, chữ tay)
  • Trả về structured data (JSON) thay vì raw text
  • Hỗ trợ tiếng Việt có dấu
  • Hiểu context tài liệu để suy luận chính xác hơn

Tiếp theo: Xem Phân tích biểu đồ và slide deck để ứng dụng Vision vào data analysis, hoặc Crop Tool khi cần đọc tài liệu với text nhỏ ở nhiều vùng.

Tính năng liên quan:VisionOCRText Extraction

Bai viet co huu ich khong?

Bản quyền thuộc về tác giả. Vui lòng dẫn nguồn khi chia sẻ.

Bình luận (0)
Ảnh đại diện
Đăng nhập để bình luận...
Đăng nhập để bình luận
  • Đang tải bình luận...

Đăng ký nhận bản tin

Nhận bài viết hay nhất về sản phẩm và vận hành, gửi thẳng vào hộp thư của bạn.

Bảo mật thông tin. Hủy đăng ký bất cứ lúc nào. Chính sách bảo mật.