A fine-tuned Qwen2.5-3B-Instruct model for Hong Kong address parsing and formatting. The model splits unstructured address text into two structured lines following Hong Kong addressing conventions.
- π Address Parsing: Splits addresses into Line 1 (specific details) and Line 2 (general location)
- ππ° Hong Kong Focus: Specialized for Hong Kong address formats (both English and Chinese)
- π Multi-language Support: Handles English, Traditional Chinese, and Simplified Chinese
- π― High Accuracy: Fine-tuned on real Hong Kong address data
- β‘ Efficient: 4-bit quantization support for memory-efficient inference
| Metric | Score (Typical) |
|---|---|
| Average Line 1 Similarity | 75-90% |
| Average Line 2 Similarity | 75-90% |
| Strict Both Lines Match | 60-75% |
| Inference Speed | ~0.5-1.0s/address |
- Python 3.9+
- CUDA-compatible GPU (24GB+ VRAM recommended)
- Git LFS (for Hugging Face uploads)
- Clone the repository
git clone https://github.com/ymlee13/address_parsing.git
cd address_parsing- Install dependencies
pip install -r requirements.txt- Download the base model (optional if you just want to test)
git lfs install
git clone https://huggingface.co/Qwen/Qwen2.5-3B-InstructThe fine-tuned LoRA adapter is available on Hugging Face Hub: ymlee13/Qwen2.5-3B-Instruct_Address_Formatter
The parser will automatically download the base model (Qwen/Qwen2.5-3B-Instruct) and the adapter from Hugging Face when you run the code for the first time.
- Prepare your data
python -c "from jsonl_converter import parse_database_file_to_nested_jsonl; parse_database_file_to_nested_jsonl('./data/database.txt', './data/database.jsonl')"- Run training
jupyter notebook train_model.ipynbjupyter notebook test_model.ipynbfrom llm_parser import HKAddressParserLLM
# Initialize parser
parser = HKAddressParserLLM(
base_model_path="Qwen/Qwen2.5-3B-Instruct",
lora_path="ymlee13/Qwen2.5-3B-Instruct_Address_Formatter",
conf_threshold=0.50,
max_new_tokens=128
)
# Parse a single address
address = "δΉιΎθ§ε‘ει²ζΌ’θ‘61θεε―§ε€§ζ¨ε°εΊ«01θ"
result = parser.parse(address)
print(f"Line 1: {result[1]}")
print(f"Line 2: {result[2]}")
# Batch parsing
addresses = [
("δΉιΎθ§ε‘ει²ζΌ’θ‘61θεε―§ε€§ζ¨ε°εΊ«01θ", ""),
("ROOM 2107, 42/F, WINNING HEIGHTS, TSUEN WAN", ""),
]
results = parser.parse_batch(addresses, batch_size=2)Try it yourself:
from llm_parser import HKAddressParserLLM
parser = HKAddressParserLLM(
base_model_path="Qwen/Qwen2.5-3B-Instruct",
lora_path="ymlee13/Qwen2.5-3B-Instruct_Address_Formatter"
)
test_cases = [
"δΉιΎθ§ε‘ει²ζΌ’θ‘61θεε―§ε€§ζ¨ε°εΊ«01θ",
"RM 2107, 42/F, WINNING HEIGHTS, 277 CASTLE PEAK RD, TSUEN WAN"
]
for addr in test_cases:
result = parser.parse(addr)
print(f"Input: {addr}")
print(f"Line 1: {result[1]}")
print(f"Line 2: {result[2]}")
print("-" * 50)address_parsing/
βββ README.md # This file
βββ requirements.txt # Python dependencies
βββ .gitignore # Git ignore file
βββ train_model.ipynb # Fine-tuning notebook
βββ test_model.ipynb # Testing and evaluation notebook
βββ llm_parser.ipynb # Inference wrapper notebook
βββ jsonl_converter.ipynb # Data conversion utility
βββ data/
β βββ database.txt # Training data (input|line1|line2)
β βββ database.jsonl # Converted training data
β βββ test_data/
β β βββ test_data.txt # Test data examples
β βββ gen_real_address.ipynb # Generate synthetic addresses
βββ models/ # Model storage (not in repo)
βββ Qwen2.5-3B-Instruct/ # Base model
βββ Qwen2.5-3B-Instruct_Address_Formatter/ # Fine-tuned adapters
##π§ Training (Optional) If you want to retrain the model:
# Convert txt to jsonl format
python -c "from jsonl_converter import parse_database_file_to_nested_jsonl; parse_database_file_to_nested_jsonl('./data/database.txt', './data/database.jsonl')"jupyter notebook train_model.ipynbjupyter notebook test_model.ipynb- Base Model: Qwen/Qwen2.5-3B-Instruct
- Fine-tuning Method: LoRA (Low-Rank Adaptation)
- Quantization: 4-bit (NF4)
- Learning Rate: 2e-5
- Epochs: 3
- Batch Size: 4 (per device)
- Gradient Accumulation: 2
- LoRA Rank: 8
- LoRA Alpha: 16
- Target Modules: q_proj, k_proj, v_proj, o_proj, gate_proj, up_proj, down_proj
- Character pooling and reconstruction
- Intelligent omission detection and re-insertion
- Language detection (Chinese/English)
- Traditional Chinese conversion
- English spell checking
##π Dataset The model was trained on a dataset of 570+ Hong Kong addresses generated from real geospatial data (ALS-GeoJSON from HK government data portal). Each address is split into:
- Line 1: Specific location (floor, unit, building)
- Line 2: General location (street, district, region) Data format:
[original input] | [line 1] | [line 2]
##π€ Inference Examples
Input:
δΉιΎθ§ε‘ει²ζΌ’θ‘61θεε―§ε€§ζ¨ε°εΊ«01θ
Output:
Line 1: εε―§ε€§ζ¨ε°εΊ«01θ
Line 2: δΉιΎθ§ε‘ει²ζΌ’θ‘61θ
Input:
ROOM 2107, 42/F, WINNING HEIGHTS, 277 CASTLE PEAK ROAD, TSUEN WAN, NEW TERRITORIES
Output:
Line 1: FLAT 2107, 42/F, WINNING HEIGHTS
Line 2: 277 CASTLE PEAK ROAD, TSUEN WAN, NEW TERRITORIES
The parser includes special handling for older GPUs:
- Disables Flash Attention
- Uses fp16 instead of 4-bit quantization when needed
- Memory-efficient batching
- Training: ~12-14GB VRAM
- Inference: ~6-8GB VRAM
- Hong Kong Government ALS-GeoJSON Dataset: https://data.gov.hk/en-data/dataset/hk-dpo-als_01-als
- Qwen2.5 Model: https://huggingface.co/Qwen/Qwen2.5-3B-Instruct
- Hugging Face Transformers: https://github.com/huggingface/transformers
- PEFT Library: https://github.com/huggingface/peft
This project is licensed under the MIT License - see the LICENSE file for details.
- Qwen for the base model
- Hugging Face for the transformers library
- Hong Kong Government for the ALS-GeoJSON dataset
- Author: ymlee13
- Hugging Face: @ymlee13
- GitHub: ymlee13