Strategi untuk pengujian unit dan pengembangan berbasis tes

16

Saya seorang penganjur besar pengembangan yang digerakkan oleh tes dalam komputasi ilmiah. Utilitas dalam praktiknya hanya mengejutkan, dan benar-benar mengurangi masalah klasik yang diketahui pengembang kode. Namun, ada kesulitan yang melekat dalam pengujian kode ilmiah yang tidak ditemukan dalam pemrograman umum, sehingga teks TDD tidak terlalu berguna sebagai tutorial. Sebagai contoh:

  • Secara umum Anda tidak tahu jawaban pasti untuk masalah kompleks yang diberikan a priori, jadi bagaimana Anda bisa menulis tes?

  • Tingkat paralelisme berubah; Saya baru-baru ini menemukan bug di mana menggunakan tugas MPI sebagai kelipatan 3 akan gagal, tetapi kelipatan 2 bekerja. Selain itu, kerangka kerja pengujian umum tampaknya tidak terlalu ramah-MPI karena sifat dasar MPI - Anda harus menjalankan kembali biner uji untuk mengubah jumlah tugas.

  • Kode ilmiah sering memiliki banyak bagian yang saling berhubungan erat, saling tergantung dan dipertukarkan. Kita semua telah melihat kode lawas, dan kita tahu betapa menggoda untuk melupakan desain yang baik dan menggunakan variabel global.

  • Seringkali metode numerik dapat berupa "eksperimen", atau pembuat kode tidak sepenuhnya memahami cara kerjanya dan mencoba memahaminya, sehingga mengantisipasi hasil tidak mungkin.

Beberapa contoh tes yang saya tulis untuk kode ilmiah:

  • Untuk integrator waktu, gunakan ODE sederhana dengan solusi yang tepat, dan uji integrator Anda menyelesaikannya dalam akurasi yang diberikan, dan urutan akurasi benar dengan menguji dengan ukuran langkah yang bervariasi.

  • Tes stabilitas nol: periksa apakah metode dengan 0 batas / kondisi awal tetap pada 0.

  • Tes interpolasi: diberi fungsi linier, pastikan interpolasi benar.

  • Validasi legacy: mengisolasi sepotong kode dalam aplikasi legacy yang diketahui benar, dan menarik beberapa nilai diskrit untuk digunakan untuk pengujian.

Masih sering muncul bahwa saya tidak tahu bagaimana cara benar menguji sepotong kode yang diberikan, selain dari coba-coba manual. Bisakah Anda memberikan beberapa contoh tes yang Anda tulis untuk kode numerik, dan / atau strategi umum untuk menguji perangkat lunak ilmiah?

Aurelius
sumber
Bisakah Anda, tolong, jelaskan apa yang Anda maksud dengan tes interpolasi?
Dmitry Kabanov

Jawaban:

8

Metode solusi buatan .

Verifikasi melalui studi perbaikan bahwa metode ini mencapai urutan akurasi teoretis.

Konservasi jawaban. Reproduksi sedikit-bijaksana dan norma-bijaksana solusi.

Bill Barth
sumber
Saya bermaksud menyebutkan MMS di posting asli; itu bagus untuk verifikasi kode, tetapi dari perspektif pengujian unit itu sama sekali tidak berharga. Jika tes-tes itu gagal, itu tidak memberikan petunjuk ke mana atau mengapa.
Aurelius
3
2×2×2
Banyak literatur yang saya lihat di MMS pada dasarnya adalah solusi global, misalnya untuk masalah CFD, solusi buatan mungkin merupakan analisis airfoil. Ketika tes ini gagal, paling tidak Anda telah mempersempit pelakunya menjadi 5.000 baris kode, jadi itu cukup berharga untuk TDD - Anda tidak memiliki petunjuk di mana kegagalan sebenarnya muncul. Saya setuju masalah 2x2x2 sangat berharga, dan saya pribadi sering menggunakannya. Tetapi cukup umum bahwa saya menemukan masalah yang hanya muncul dengan sistem yang lebih besar; Saya benar-benar menemukan bug kompilator ifort baru-baru ini yang hanya terwujud dalam masalah besar.
Aurelius
@ Aurelius: Tidak ada argumen di sini. Anda harus memiliki serangkaian tes dan menjalankan semuanya sering.
Bill Barth
@Aurelius Pada nilai nominal, MMS bukan tes unit, tetapi tes fungsional atau penerimaan (yaitu dari keseluruhan sistem). Namun, kode seringkali memiliki tahapan yang terpisah (atau dapat dibagi ke dalamnya). misalnya adveksi, tekanan, viskositas. Seseorang kemudian dapat menguji hanya satu dari tahapan ini ("unit"). Demikian pula, kode dapat diuji tanpa BC, dan kemudian dengan satu. Seorang teman melakukan PhD-nya pada unit testing, dan dia menganggap manfaat terbesar adalah memaksa Anda untuk memecah program Anda menjadi unit, sehingga dapat diuji unit ... mungkin ini lebih berlaku di sini daripada yang tampak pada awalnya (dan dengan cara lain saya tidak tahu).
hyperpallium
6

Bill telah membuat daftar beberapa metode untuk mengatasi masalah Anda.

Mengatasi poin ketiga Anda, tidak, tidak ada alasan untuk memperkenalkan kopling yang kuat antar bagian. Justru sebaliknya: jika fungsi atau kelas Anda memiliki antarmuka yang terdefinisi dengan baik, akan lebih mudah untuk bertukar misalnya pemecah linear untuk yang lain, atau skema loncatan waktu. Tolak saja, dan kemudian Anda akan dapat menguji komponen-komponen ini secara terpisah. Kami telah melakukan ini dengan kesepakatan. II selama beberapa dekade.

Ke poin keempat: jika metode Anda adalah eksperimen, percobaan Anda dengan metode tersebut merupakan ujian. Selama Anda tidak memiliki analisis, Anda harus mengambil hasil tes ini sebaik mungkin. Tetapi biasanya, Anda memiliki harapan misalnya untuk urutan metode, atau Anda akan tahu itu tepat untuk kelas solusi tertentu, misalnya polinomial hingga tingkat tertentu. Memverifikasi ini harus menjadi bagian dari eksperimen Anda, dan ketika analisis meningkat, tes dapat ditambahkan.

Guido Kanschat
sumber
1
Untuk menambah jawaban Guido, pengalaman yang ia ajak bicara disandikan dalam ~ 3.000 tes yang kami jalankan secara otomatis.II setelah setiap perubahan: dealii.org/developer/development/… . Pada pertanyaan tentang apa yang harus dilakukan jika Anda tidak tahu jawaban yang tepat: tetap tulis tes dan biarkan membandingkan jawaban hari ini dengan jawaban kemarin (atau setiap kali Anda menulis tes). Memiliki cara untuk menemukan perubahan dalam output kode sangat berharga bahkan jika Anda tidak tahu apakah mereka membuat jawaban salah atau mengoreksi jawaban yang sebelumnya salah.
Wolfgang Bangerth
3

Saya baru-baru ini menemukan tesis ini pada TDD dalam Ilmu Komputasi. Saya belum membacanya jadi saya tidak tahu apakah itu bagus, tapi mudah-mudahan ini bisa membantu.

http://cyber.ua.edu/files/2014/12/u0015_0000001_0001551.pdf

majalah
sumber
1
Saya membaca beberapa intro dan kesimpulan, dan mengasumsikan tingkat kualitas setara dengan tesis PhD standar, ini menjelaskan proses (dengan cara tingkat tinggi) dan memberikan pengukuran aktual mengenai efektivitasnya. Saya pikir ini cukup menemukan.
Godric Seer
Tautannya sudah mati. Apakah maksud Anda: Nanthaamornphong, A. "Efektivitas pengembangan yang didorong oleh tes dan teknik refactoring dalam ilmu komputasi dan pengembangan perangkat lunak rekayasa". PhD diss., Uni. Alabama (2014).
AlQuemist