Lihat juga: Parsing
pengantar
Anda sedang bekerja di tim pemrograman pemerintah, yang telah memprogram kamera kecepatan. Namun, sekelompok orang yang telah memprogram kalkulator kecepatan telah mengambil terlalu banyak ruang, jadi Anda harus membuat perangkat lunak pengenalan plat nomor sekecil mungkin.
Tantangan
Diberi gambar pelat nomor, kembalikan teks di piring.
Plat nomor
Berikut ini adalah semua karakter yang harus dikenali oleh program Anda:
ABCDEFG
H1JKLMN0
PQRSTUVW
XYZ01234
56789
Catatan
Pada pelat nomor Inggris, karakter untuk I (i) dan 1 (satu) adalah sama dan karakter untuk O (o) dan 0 (nol) adalah sama. Karena itu, selalu anggap karakter adalah angka. Yaitu plat nomor berikut adalah 10 (satu nol):
Contohnya
C0D3 GLF
B3T4 DCY
M1NUS 15
YET1CGN
Aturan lainnya
Akses Internet dan pustaka dan fungsi OCR tidak diizinkan.
Pelat nomor akan selalu terlihat identik dengan yang ditunjukkan di atas. Semua pelat nomor akan berukuran hampir sama (akan ada beberapa ketidakakuratan karena metode tanam).
Jika Anda membutuhkan versi PNG lossless pelat nomor apa pun, saya akan menyediakannya untuk Anda.
Mencetak gol
Program terpendek dalam byte menang.
Semua pelat nomor adalah tangkapan layar bilah pencarian di situs ini
sumber
Jawaban:
C, 409 byte (dan saya sama terkejutnya dengan siapa pun)
Diambil sebagai input: lebar (
w
) dan tinggi (h
) dari gambar, diikuti oleh data RGB yang dikemas sebagai larikchar
s (d
). Semua parameter fungsi lainnya adalah deklarasi variabel yang menyamar. Abaikan semuanya kecuali saluran hijau, dan terapkan ambang batas 32 sebagai lintasan awal.Sebagian besar sama dengan metode @ DavidC, kecuali ini memeriksa bahwa setidaknya 35% dari setiap kotak sampel diisi. Semoga itu membuatnya lebih kuat untuk mengukur perubahan, tetapi siapa yang tahu.
Saya menggunakan metode brute-force untuk mengetahui ukuran resampling dan persen cakupan yang digunakan untuk keandalan terbaik (yaitu kasus paling sedikit dari satu karakter yang memiliki beberapa interpretasi). Ternyata kisi 4x5 dengan cakupan 35% adalah yang terbaik. Saya kemudian menggunakan metode brute-force kedua untuk menghitung pengaturan bit terbaik dan nilai modulo untuk mengemas data karakter menjadi string pendek - bit rendah di kiri atas, meningkat dalam x lalu y, dengan nilai akhir% 101 berubah yang terbaik, berikan tabel pencarian ini:
Mengurangi 7 berarti inisial dapat dihapus, dan 2 yang terakhir dapat dihapus tanpa kerja ekstra. Penghapusan ini berarti bahwa input tertentu yang tidak valid dapat menyebabkan memori yang tidak valid terbaca, sehingga dapat memisahkan gambar tertentu.
Pemakaian:
Untuk mendapatkan gambar ke dalamnya, saya menulis pembungkus menggunakan libpng. Juga ternyata meskipun memiliki nama file, gambar dalam pertanyaan sebenarnya adalah jpegs (!), Jadi Anda harus mengekspornya secara manual sebagai pngs terlebih dahulu.
Kerusakan
sumber
Mathematica
1170 1270 1096 1059 650 528 570 551 525498 byteVersi terbaru menghemat 27 byte dengan tidak mengharuskan plat "dipangkas" sebelum diuraikan. Versi kedua terakhir menyimpan 26 byte dengan hanya menggunakan 10 dari 24 titik sampel asli.
122 byte disimpan melalui ide LegionMammal978 tentang pengemasan daftar panjang nomor basis 10 sebagai nomor tunggal, nomor 36. Dia mengupas 20 byte lagi dari kode akhir.
Lompatan dari 528 ke 570 byte adalah karena kode tambahan untuk memastikan bahwa urutan surat-surat yang dikembalikan sesuai dengan urutan surat-surat di plat nomor. Centroid untuk setiap huruf berisi koordinat x, yang mengungkapkan posisi relatif huruf sepanjang x.
Kode Tidak Terkunci
Ikhtisar
Ide dasarnya adalah untuk memeriksa apakah pengambilan sampel piksel secara sistematis dari gambar input cocok dengan piksel dari lokasi yang sama pada gambar bonafide. Sebagian besar kode terdiri dari tanda tangan bit untuk setiap karakter,
Diagram menunjukkan piksel yang diambil dari huruf "J", "P", "Q", dan "R".
Nilai piksel dapat direpresentasikan sebagai matriks. Gelap, tebal
1
berhubungan dengan sel hitam. Ini0
sesuai dengan sel putih.Ini adalah aturan penggantian dekripsi untuk JPQ R.
{1, 1, 1, 1, 9, 15} -> "J",
{15, 9, 15, 14, 8, 8} -> "P",
{15, 9, 9, 9, 9, 15, 15 } -> "Q",
{15, 9, 15, 14, 10, 11} -> "R"
Seharusnya dimungkinkan untuk memahami mengapa aturan untuk "0" adalah:
{15, 9, 9, 9, 9, 15} -> "0"
dan dengan demikian dapat dibedakan dari huruf "Q".
Berikut ini menunjukkan 10 poin yang digunakan dalam versi final. Poin-poin ini cukup untuk mengidentifikasi semua karakter.
Apa fungsinya
plateCrop[img]
menghilangkan bingkai dan tepi kiri dari piring, membuat latar belakang putih. Saya dapat menghilangkan fungsi ini dari versi final dengan memilih komponen gambar, kemungkinan huruf yang tingginya antara 100 dan 120 piksel.isolateLetters[img]
menghapus setiap huruf dari gambar yang dipangkas.Kita dapat menampilkan cara kerjanya dengan menunjukkan di mana gambar yang dipangkas, output dari
plateCrop
masuk sebagai input untukisolateLetters
. Outputnya adalah daftar karakter individu.Coordinates
adalah 24 posisi yang didistribusikan secara merata untuk memeriksa warna piksel. Koordinat sesuai dengan yang ada di gambar pertama.{{9, 99}, {27, 99}, {45, 99}, {63, 99}, {9, 81}, {27, 81}, {45, 81}, {63, 81}, { 9, 63}, {27, 63}, {45, 63}, {63, 63}, {9, 45}, {27, 45}, {45, 45}, {63, 45}, {9, 27}, {27, 27}, {45, 27}, {63, 27}, {9, 9}, {27, 9}, {45, 9}, {63, 9}}
h
mengubah piksel menjadi biner.codes
adalah tanda tangan untuk setiap karakter. Nilai desimal adalah singkatan dari kode biner untuk sel hitam (0) dan Putih (1). Dalam versi golf, base 36 digunakan.(*
decryptRules
untuk mengganti tanda tangan dengan karakter masing-masing *)f
adalah fungsi yang mengambil gambar plat dan mengembalikan surat.{"A", "B", "C", "D", "E", "F", "G"}
{"H", "1", "J", "K", "K", "L", "M", "N", "0"}
{"P", "Q", "R", "S", "T", "U", "V", "W"}
{"X", "Y", "Z", "0", "1", "2", "3", "4"}
{"5", "6", "7", "8", "8", "9"}
Golf
Kode ini disingkat dengan menggunakan angka desimal tunggal untuk mewakili semua 24 bit (putih atau hitam) untuk setiap karakter. Misalnya, huruf "J" menggunakan aturan pengganti berikut:
1118623 -> "J"
.1118623 berkorespondensi dengan
{0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 1, 1, 1}
yang dapat dikemas ulang sebagai
{{0, 0, 0, 1}, {0, 0, 0, 1}, {0, 0, 0, 1}, {0, 0, 0, 1}, {1, 0, 0, 1} , {1, 1, 1, 1}}
yang hanya merupakan matriks untuk "J" yang kita lihat di atas.
Penghematan lain datang dari mewakili alfabet
"0123456789ABCDEFGHJKLMNPQRSTUVWXYZ"
bukan sebagai daftar huruf.Akhirnya, semua fungsi dari versi panjang, kecuali
h
, diintegrasikan ke dalam fungsif
daripada ditentukan secara terpisah.sumber
{1118623, 2518818, ..., 16645599}
dengan ini .x[[All,2,1]]
dapat diganti denganx[[;;,2,1]]
.Flatten[x,1]
sama denganJoin@@x
, danFlatten[#,1]&/@x
setara denganJoin@@@x
. Ada beberapa optimasi kecil lainnya yang dapat dilakukan. Kode 551-byte setelah golf ini.C #,
10401027 byteTidak Terkumpul:
Pada dasarnya saya menemukan beberapa titik referensi khusus untuk memeriksa kuning / hitam untuk menentukan identitas masing-masing karakter.
sumber
csc.exe main.cs /r:System.Drawing.dll
PHP -
174116741143 bytePertama kali diatur dengan mempelajari profil karakter dari beberapa contoh pertama, yang kemudian merangkum setiap karakter menjadi enam angka. Saya memilih enam karena pada awalnya saya punya lima, dan itu tidak bekerja sebaik yang saya inginkan, tetapi enam tampaknya bekerja lebih baik. Sebagian besar optimasi melibatkan memeras profil-profil ini menjadi jumlah byte yang lebih kecil dan lebih kecil.
Profil pertama dan kedua
*lhdfdn
dan|nnmmkk
sebenarnya adalah gumpalan biru dengan "GB" di bagian bawah*
, dan batas kanan|
, yang kita abaikan. Lebih aman untuk memasukkan mereka sehingga gumpalan dan perbatasan kanan memiliki sesuatu yang cocok.Harus menangani format gambar apa pun, penskalaan beralasan apa pun asalkan rasio aspek tidak berubah terlalu banyak, warna gelap pada warna terang, dan bahkan sedikit noise dan bayangan!
Memang perlu perbatasan, setidaknya di bagian atas dan bawah, itu bagian dari profil.
Simpan sebagai
ocr.php
, lalu jalankan dari baris perintah:Bagi mereka yang tertarik, berikut adalah kode pembelajarannya. Simpan sebagai
learn.php
dan jalankan dari baris perintah, tanpa argumen.sumber
PHP,
971970 byteMenarik berat pada Yimin Rong 's jawaban , yang dapat serius golfed bawah, terutama indeks array, dan dimasukkan ke dalam Phar dengan kompresi gzip.
Unduh phar
Ini adalah versi dasar saya yang ditingkatkan pada
15571535 byte, disimpan hanya dengan nama file "o":Perbaikan:
Tahap 1
Tahap 2
intval
dengan~~
(menyimpan 8 byte, dua kejadian)file_get_contents($u)
diganti denganjoin('',file($u))
(menghemat 5 byte)Sayangnya, semua peningkatan tahap kedua hanya diterjemahkan menjadi 1 byte lebih sedikit kode gzip. :-D
Dan kode ini digunakan untuk membuat Phar:
Uji dengan
php ocr.phar http://i.imgur.com/i8jkCJu.png
atau gambar kasus uji lainnya.sumber