Jadi, dalam upaya saya untuk menulis sebuah program untuk mengkonjugasikan kata kerja (secara algoritmik, bukan melalui dataset) untuk bahasa Prancis, saya menemukan sedikit masalah.
Algoritma untuk mengkonjugasikan kata kerja sebenarnya cukup sederhana untuk 17 atau lebih kasus kata kerja, dan berjalan pada pola tertentu untuk setiap kasus; dengan demikian, sufiks konjugasi untuk 17 kelas ini bersifat statis dan akan (sangat mungkin) tidak berubah dalam waktu dekat. Sebagai contoh:
// Verbs #1 : (model: "chanter")
terminations = {
ind_imp: ["ais", "ais", "ait", "ions", "iez", "aient"],
ind_pre: ["e", "es", "e", "ons", "ez", "ent"],
ind_fut: ["erai", "eras", "era", "erons", "erez", "eront"],
participle: ["é", "ant"]
};
Ini adalah sufiks infleksi untuk kelas kata kerja yang paling umum dalam bahasa Prancis.
Ada kelas-kelas lain dari kata kerja (irreguler), yang konjugasinya juga sangat mungkin tetap statis untuk satu atau dua abad berikutnya. Karena tidak teratur, konjugasi lengkapnya harus dimasukkan secara statis, karena konjugasi tidak dapat diandalkan dari suatu pola (hanya ada juga [menurut hitungan saya] 32 irreguler). Sebagai contoh:
// "être":
forms = {
ind_imp: ["étais", "étais", "était", "étions", "étiez", "étaient"],
ind_pre: ["suis", "es", "est", "sommes", "êtes", "sont"],
ind_fut: ["serai", "seras", "sera", "serons", "serez", "seront"],
participle: ["été", "étant"]
};
Saya bisa memasukkan semua ini ke XML atau bahkan JSON dan membatalkan deserialize ketika itu perlu digunakan, tetapi apakah ada benarnya? String ini adalah bagian dari bahasa alami, yang memang berubah, tetapi pada tingkat yang lambat.
Kekhawatiran saya adalah bahwa dengan melakukan hal-hal dengan cara yang "benar" dan deserialisasi beberapa sumber data, saya tidak hanya rumit masalah yang tidak perlu rumit, tetapi saya juga benar-benar kembali melacak seluruh tujuan dari pendekatan algoritmik: untuk tidak menggunakan sumber data! Dalam C #, saya hanya bisa membuat kelas di bawah namespace Verb.Conjugation
(misalnya class Irregular
) untuk menempatkan string ini dalam tipe enumerated atau sesuatu, daripada memasukkannya ke dalam XML dan membuat a class IrregularVerbDeserializer
.
Jadi pertanyaannya: apakah itu sesuai untuk string hard-code yang sangat tidak mungkin berubah selama masa aplikasi? Tentu saja saya tidak dapat menjamin 100% bahwa mereka tidak akan berubah, tetapi risiko vs biaya hampir sepele untuk ditimbang di mata saya - hardcoding adalah ide yang lebih baik di sini.
Sunting : Duplikat yang diajukan menanyakan bagaimana cara menyimpan sejumlah besar string statis , sementara pertanyaan saya adalah kapan saya harus membuat hard- string string statis ini .
Jawaban:
Sepertinya saya menjawab pertanyaan Anda sendiri.
Salah satu tantangan terbesar yang kita hadapi adalah memisahkan hal-hal yang cenderung berubah dari hal-hal yang tidak akan berubah. Beberapa orang menjadi gila dan membuang semua yang mereka bisa ke dalam file konfigurasi. Yang lain pergi ke ekstrim lain dan membutuhkan kompilasi ulang untuk perubahan yang paling jelas sekalipun.
Saya akan menggunakan pendekatan yang paling mudah untuk diterapkan sampai saya menemukan alasan kuat untuk membuatnya lebih rumit.
sumber
French.Verb.Irregular.Etre
yang akan berisi data dari pertanyaan saya. Saya pikir itu bekerja dengan baik;)if (num == 0xFFD8)
). Contoh itu harus menjadi sesuatu sepertiif (num == JPEG_MAGIC_NUMBER)
di hampir semua kasus untuk alasan keterbacaan. Saya hanya menunjukkannya karena kata "hardcoding" sering menimbulkan bulu di leher orang (seperti milik saya) karena makna kata alternatif ini.JPEG_START_OF_IMAGE_MARKER
?Anda beralasan pada ruang lingkup yang salah.
Anda belum mengkodekan satu-satunya kata kerja individual. Anda telah mendodekan bahasa dan aturannya . Ini, pada gilirannya, berarti bahwa aplikasi Anda tidak dapat digunakan untuk bahasa lain, dan tidak dapat diperpanjang dengan aturan lain.
Jika ini maksud Anda (yaitu menggunakannya hanya untuk bahasa Prancis), ini adalah pendekatan yang tepat, karena YAGNI. Tetapi Anda mengakui bahwa Anda juga ingin menggunakannya nanti untuk bahasa lain, yang artinya segera, Anda harus memindahkan semua bagian yang sudah dikodekan ke file konfigurasi. Pertanyaan yang tersisa adalah:
Apakah Anda, dengan kepastian mendekati 100%, dalam waktu dekat, memperluas aplikasi ke bahasa lain? Jika demikian, Anda seharusnya mengekspor barang ke file JSON atau XML (untuk kata-kata, bagian dari kata, dll.) Dan bahasa dinamis (untuk aturan) sekarang daripada memaksa diri Anda untuk menulis ulang bagian utama aplikasi Anda.
Atau hanya ada kemungkinan kecil bahwa aplikasi akan diperpanjang di suatu tempat di masa depan, dalam hal mana YAGNI menentukan bahwa pendekatan paling sederhana (yang Anda gunakan saat ini) lebih baik?
Sebagai ilustrasi, ambil pemeriksa ejaan Microsoft Word. Menurut Anda, berapa banyak hal yang dikodekan dengan hardcode?
Jika Anda mengembangkan prosesor teks, Anda bisa mulai dengan mesin ejaan sederhana dengan aturan hardcode dan bahkan kata - kata
if word == "musik": suggestSpelling("music");
. Dengan cepat, Anda akan mulai memindahkan kata, lalu mengatur sendiri di luar kode Anda. Jika tidak:Saat Anda menyorot diri sendiri:
Segera setelah Anda meng-hardcode aturan untuk suatu bahasa, setiap yang lain akan membutuhkan kode yang semakin banyak, terutama mengingat kompleksitas bahasa alami.
Subjek lain adalah bagaimana Anda mengekspresikan aturan yang berbeda, jika tidak melalui kode. Pada akhirnya, Anda mungkin menemukan bahwa bahasa pemrograman adalah alat terbaik untuk itu. Dalam hal ini, jika Anda perlu memperpanjang mesin tanpa mengkompilasi ulang, bahasa dinamis mungkin merupakan alternatif yang baik.
sumber
LanguageProcessor
kelas dengan beberapa subclass. (Secara efektif, "file konfigurasi" sebenarnya adalah sebuah kelas)String harus diekstraksi ke file konfigurasi atau database ketika nilai-nilai bisa berubah secara independen dari logika program.
Sebagai contoh:
Mengekstrak teks UI ke file sumber daya. Ini memungkinkan non-programmer untuk mengedit dan membaca bukti teks, dan memungkinkan menambahkan bahasa baru dengan menambahkan file sumber daya lokal baru.
Mengekstrak string koneksi, url ke layanan eksternal, dll. Ke file konfigurasi. Ini memungkinkan Anda untuk menggunakan konfigurasi yang berbeda di lingkungan yang berbeda, dan untuk mengubah konfigurasi dengan cepat karena mungkin perlu diubah karena alasan di luar aplikasi Anda.
Pemeriksa ejaan yang memiliki kamus kata untuk diperiksa. Anda dapat menambahkan kata dan bahasa baru tanpa mengubah logika program.
Tetapi ada juga overhead kompleksitas dengan mengekstraksi ke konfigurasi, dan itu tidak selalu masuk akal.
String dapat di- hardcode ketika string aktual tidak dapat berubah tanpa mengubah logika program.
Contoh:
Dalam kasus Anda, saya pikir jelas bahwa kata-kata adalah bagian yang terintegrasi dari logika program (karena Anda sedang membangun konjugator dengan aturan khusus untuk kata-kata tertentu), dan mengekstraksi kata-kata ini ke file eksternal tidak memiliki nilai.
Jika Anda menambahkan bahasa baru, Anda tetap harus menambahkan kode baru, karena setiap bahasa memiliki logika konjugasi tertentu.
Beberapa menyarankan agar Anda dapat menambahkan semacam mesin aturan yang memungkinkan Anda menentukan aturan konjugasi untuk bahasa yang arbitrer, sehingga bahasa baru dapat ditambahkan murni dengan konfigurasi. Pikirkan baik-baik sebelum Anda menyusuri jalan itu, karena bahasa manusia sangat aneh sehingga Anda perlu mesin aturan yang sangat ekspresif. Anda pada dasarnya akan menciptakan bahasa pemrograman baru (DSL konjugasi) untuk keuntungan yang meragukan. Tetapi Anda sudah memiliki bahasa pemrograman yang Anda inginkan yang dapat melakukan apa pun yang Anda butuhkan. Bagaimanapun, YAGNI.
sumber
Saya setuju 100% dengan jawaban Dan Pichelman, tetapi saya ingin satu hal ditambahkan. Pertanyaan yang harus Anda tanyakan pada diri Anda di sini adalah "siapa yang akan mempertahankan / memperluas / memperbaiki daftar kata?". Jika selalu orang yang juga memelihara aturan bahasa tertentu (pengembang tertentu, saya kira Anda), maka tidak ada gunanya menggunakan file konfigurasi eksternal jika ini membuat segalanya lebih rumit - Anda tidak akan mendapat manfaat dari ini. Dari sudut pandang ini, masuk akal untuk membuat hardcode daftar kata tersebut bahkan jika Anda harus mengubahnya dari waktu ke waktu, selama itu cukup untuk mengirimkan daftar baru sebagai bagian dari versi baru.
(Di sisi lain, jika ada sedikit peluang seseorang harus dapat mempertahankan daftar di masa depan, atau jika Anda perlu mengubah daftar kata tanpa menggunakan versi baru aplikasi Anda, maka gunakan file terpisah.)
sumber
Bahkan walaupun hardcoding tampaknya baik-baik saja di sini, dan lebih baik daripada secara dinamis memuat file konfigurasi, saya masih akan merekomendasikan agar Anda benar-benar memisahkan data Anda (kamus kata kerja) dari algoritma . Anda dapat mengompilasinya langsung ke dalam aplikasi Anda dalam proses pembuatan.
Ini akan menghemat banyak hazzle dengan pemeliharaan daftar. Di VCS Anda, Anda dapat dengan mudah mengidentifikasi apakah komit mengubah algoritma, atau hanya memperbaiki bug konjugasi. Juga, daftar mungkin perlu ditambahkan di masa depan untuk kasus-kasus yang tidak Anda pertimbangkan. Terutama, jumlah 32 kata kerja tidak beraturan yang Anda hitung tampaknya tidak tepat. Sementara itu tampaknya mencakup yang umum digunakan, saya menemukan referensi ke 133 atau bahkan 350 di antaranya.
sumber
Bagian yang penting adalah pemisahan perhatian. Bagaimana Anda mencapainya itu kurang relevan. yaitu Java baik-baik saja.
Terlepas dari bagaimana aturan diekspresikan, haruskah Anda perlu menambahkan bahasa perubahan aturan: berapa banyak kode dan file yang harus Anda edit?
Idealnya, menambahkan bahasa baru harus dimungkinkan dengan menambahkan file 'english.xml' atau yang baru 'EnglishRules mengimplementasikan objek ILanguageRules'. File teks (JSON / XML) memberi Anda keuntungan jika Anda ingin mengubahnya di luar siklus hidup build Anda, tetapi membutuhkan tata bahasa yang rumit, penguraian, dan akan lebih sulit untuk di-debug. File kode (Java) memungkinkan Anda mengekspresikan aturan yang rumit dengan cara yang lebih sederhana, tetapi membutuhkan pembangunan kembali.
Saya akan mulai dengan Java API sederhana di belakang antarmuka agnostik bahasa bersih - seperti yang Anda butuhkan dalam kedua kasus. Anda selalu dapat menambahkan implementasi antarmuka yang didukung oleh file XML nanti jika Anda mau, tapi saya tidak melihat kebutuhan untuk segera mengatasi masalah itu (atau pernah).
sumber