Khi hai vế của phép so sánh khác kiểu, database phải ép một vế về kiểu kia. Nếu vế bị ép là cột, index trên cột đó trở nên vô dụng — hoàn toàn giống trường hợp bọc cột trong hàm, chỉ khác là lần này database tự thêm hàm giúp bạn.
Tình huống kinh điển ở MySQL: cột phone VARCHAR(20), truy vấn truyền vào số.
-- phone is VARCHAR, 0901234567 is a number
-- MySQL converts every phone value to a number: index unusable
SELECT * FROM users WHERE phone = 0901234567;
-- correct: compare string to string
SELECT * FROM users WHERE phone = '0901234567';Quy tắc của MySQL là khi so sánh chuỗi với số thì chuỗi bị ép sang số, nên cột luôn là bên chịu thiệt. Kết quả còn có thể sai chứ không chỉ chậm: '0901234567' và '901234567' ép sang số đều bằng nhau.
PostgreSQL chặt về kiểu hơn nên thường báo lỗi thay vì âm thầm ép, nhưng vẫn dính khi trộn int với bigint/numeric trong join, hoặc khi driver gửi tham số dưới dạng text.
Cách phát hiện: đọc EXPLAIN — nếu điều kiện hiện ra dạng (phone)::numeric = ... hoặc MySQL báo type: ALL dù có index, gần như chắc chắn là ép kiểu. Cách sửa: để kiểu tham số khớp kiểu cột (dùng prepared statement với đúng kiểu), hoặc sửa kiểu cột nếu schema sai từ đầu.