Bagaimana sistem tipe statis mempengaruhi desain bahasa berbasis prototipe?


15

The artikel Wikipedia pada bahasa berbasis prototipe berisi paragraf berikut:

Hampir semua sistem berbasis prototipe didasarkan pada bahasa yang ditafsirkan dan diketik secara dinamis. Namun, sistem yang didasarkan pada bahasa yang diketik secara statis layak secara teknis.

Dalam hal apa sistem tipe statis memaksakan pembatasan atau memperkenalkan kompleksitas dalam bahasa berbasis prototipe, dan mengapa ada bahasa prototipe yang diketik secara lebih dinamis?


2
+1 dan favorit: Saya telah merenungkan hal itu sendiri untuk beberapa waktu, dan tidak menemukan masalah yang sangat sulit dengan sistem tipe struktural . Sebenarnya, ini sangat mengganggu saya sehingga saya ingin maju dan mencoba membuat bahasa berbasis prototipe yang diketik secara statis hanya untuk melihat masalah apa yang ada ...

Saya baru memulai proses itu sendiri untuk alasan yang sama :)
Joe

Jawaban:


6

Batas antara tipe fundamental dan objek kabur dan sering secara artifisial diperkenalkan. Sebagai contoh, Di C sebuah struct hanya sekelompok catatan, hanya tipe non-objek turunan. Dalam C ++, sebuah struct adalah kelas dengan semua bidang publik, sebuah objek. Namun, C ++ hampir sepenuhnya kompatibel dengan C ... perbatasannya sangat lembut di sini.

Untuk pemrograman berbasis prototipe Anda harus memiliki objek yang bisa berubah saat runtime. Mereka HARUS diketik lunak karena setiap perubahan saat runtime, kelas dari satu jenis berubah menjadi yang lain - jenisnya berubah.

Anda mungkin menjaga tipe fundamental dan turunan non-objek sebagai statis sekalipun. Tapi ini menimbulkan perbedaan yang aneh, objek diketik dengan lembut, bukan obyek diketik statis, dan barier yang keras harus dibuat di antara keduanya. Haruskah Anda dapat mengubah struktur? Sebuah benang? Haruskah Angka menjadi kelas atau tipe fundamental, atau sekumpulan tipe fundamental, int / float / bignum / etc?

Itu hanya lebih alami dan mudah dipelajari, digunakan dan ditulis untuk memiliki seragam ini, semua jenis bisa berubah atau tidak ada jenis yang bisa berubah saat runtime. Jika Anda menyatakan hanya satu jenis (Objek) yang bisa berubah, Anda berakhir dengan sakit kepala dan masalah kedua dunia.

Ketik-statis adalah:

  • lebih mudah diimplementasikan
  • lebih cepat / lebih efisien
  • lebih aman
  • lebih mudah untuk memelihara / mendokumentasikan sistem besar karena abstraksi.

Ketik dinamis adalah:

  • lebih cepat menulis,
  • lebih ringkas
  • Bahasa lebih mudah dipelajari
  • lebih memaafkan untuk kesalahan desain.

Dengan memadukan keduanya, Anda banyak berkorban.

  • Implementasi menjadi lebih sulit daripada dua yang sebelumnya.
  • kecepatan tergantung apakah Anda menggunakan tipe lunak atau tidak ... Jika ya, rendah, jika tidak, mengapa memilih bahasa sama sekali?
  • tipe safety keluar jendela untuk semua tipe objek.
  • mengikuti bagaimana satu jenis berubah menjadi yang lain adalah tugas yang cukup sulit. Mendokumentasikannya - sangat sulit.
  • Anda masih perlu melakukan semua pembukuan dengan tipe dasar, yang membunuh keringkasan dan kecepatan menulis
  • Kompleksitas bahasa lebih tinggi (lebih sulit untuk dipelajari) daripada yang "spesifik",
  • "forgiving" dari dynamic-typed digantikan oleh kecenderungan untuk beberapa kesalahan yang sangat sulit pada tipe atribut yang tidak cocok.

1
Pikiran untuk memberikan contoh mengapa objek harus "bisa berubah-ubah" (Saya berasumsi maksud Anda penambahan dan penghapusan atribut, tidak mengubah mereka, karena itu biasanya tidak terkait dengan mengetik).

@delnan: tidak juga, dalam pemrograman berbasis prototipe Anda dapat menggali isi suatu objek sesuai keinginan Anda, menghapus, menambah, mengganti, menutupi, baik metode maupun atribut secara langsung. Itulah intinya dan penggantian fleksibel yang sangat nyaman untuk memodifikasi objek melalui aturan kaku warisan klasik. Jika suatu bahasa menggunakan Kelas sebagai Tipe, Anda tidak dapat mengubah strukturnya dengan cepat jika jenisnya tidak lunak.
SF.

1
Saya kira tidak. Dengan logika yang sama, orang dapat berargumentasi bahwa pemrograman berbasis kelas membutuhkan kebebasan yang sama seperti bahasa dinamis berbasis kelas memungkinkan ini. Tidak, prototipe statis dengan sistem tipe struktural akan membubuhi keterangan objek dengan daftar anggotanya dan secara rekursif tipenya, dan memeriksa secara statis bahwa anggota ini ada (dan memiliki jenis yang tepat) dengan mengharuskan semua anggota diberikan pada saat pembuatan objek atau hadir di prototipe dan tidak termasuk cara untuk menghapus anggota. Hasilnya masih terlihat cukup prototipish bagi saya dan menjamin bahwa setiap anggota hadir setiap saat.

@delnan: Anda baru saja menjelaskan warisan klasik melalui komposisi. Ya, itu terlihat sangat prototypish dan merupakan (sangat nerfed) cara melakukan pemrograman berbasis prototipe dalam bahasa model pewarisan klasik. Itu hanya menghilangkan pb.p dari 90% kesenangan, membunuh keuntungan terbesarnya (dan sekaligus menghilangkan bahaya terbesar). Ya, dalam analogi penembakan kaki yang lama, pb.p berfitur lengkap akan membantu Anda menembak kedua kaki Anda dengan sendok teh. Jika Anda tidak menyukai kekuatan semacam ini, Anda sebaiknya tetap berpegang pada warisan klasik.
SF.

1
Anda bingung "dinamis" dengan "prototipe". Kebebasan ini yang tidak berbaur dengan baik dengan sistem tipe statis bukan fitur prototipe, mereka adalah fitur dinamika. Tentu saja menambahkan pengetikan statis mencegah mereka, tetapi mereka bukan bagian dari prototipe (itu IMGO terutama kurangnya kelas yang mendukung objek kloning untuk bertindak sebagai orang tua). Dinamisme itu ortogonal bagi prototipe. Semua bahasa prototipe populer kebetulan termasuk mereka, tetapi mereka independen dari prototipe seperti yang dinyatakan sebelumnya. Pertimbangkan cuplikan ini dalam bahasa fiksi: pastebin.com/9pLuAu9F . Bagaimana ini bukan prototipe?

3

Kesulitannya cukup mudah untuk dilihat: Mengambil tampilan objek sebagai kamus metode, atau sebagai hal-hal yang merespons pesan, perhatikan hal berikut tentang bahasa OO umum yang diketik secara statis:

  • Semua kunci kamus / pesan secara umum dideklarasikan terlebih dahulu, menggunakan pengidentifikasi yang dideklarasikan secara statis.

  • Set pesan tertentu dideklarasikan sebelumnya, dan objek dikaitkan dengan set ini untuk menentukan pesan mana yang mereka respons.

  • Hubungan inklusi dari satu set pesan menjadi subset dari yang lain dinyatakan secara statis dan eksplisit; tidak diumumkan tetapi subset logis tidak valid.

  • Pengecekan jenis upaya untuk memastikan bahwa semua pesan dikirim hanya ke objek yang menanggapi mereka.

Setiap konflik ini sampai batas tertentu dengan sistem berbasis prototipe:

  • Nama pesan dapat dideklarasikan terlebih dahulu, dalam bentuk "atom" atau string yang diinternir atau yang lainnya, tetapi hanya sedikit; plastisitas objek berarti menetapkan tipe ke metode adalah canggung.

  • Ini bisa dibilang fitur penting dari sistem berbasis prototipe yang set pesan didefinisikan oleh apa yang ditanggapi oleh suatu objek, bukan sebaliknya. Masuk akal untuk menetapkan alias ke kombinasi tertentu pada waktu kompilasi, tetapi set pesan yang ditentukan saat runtime harus dimungkinkan.

  • Dampak nyata dari dua hal di atas menyentuh rumah dengan hubungan inklusi, di mana deklarasi eksplisit sama sekali tidak bisa dijalankan. Warisan dalam pengertian subtyping nominal yang statis bertentangan dengan sistem berbasis prototipe.

Yang membawa kita ke titik akhir, yang sebenarnya tidak ingin kita ubah. Kami masih ingin memastikan bahwa pesan hanya dikirim ke objek yang meresponsnya. Namun:

  • Kami tidak dapat mengetahui secara statis pesan apa yang mungkin dikelompokkan bersama.
  • Kita tidak bisa tahu pengelompokan mana yang merupakan himpunan bagian dari yang lain.
  • Kita tidak bisa tahu pengelompokan mana yang mungkin.
  • Kami bahkan tidak dapat menentukan argumen apa yang dikirim bersama dengan satu pesan.
  • Pada dasarnya kami menemukan bahwa kami tidak dapat menentukan banyak hal sama sekali dalam kasus yang sepenuhnya umum.

Jadi bagaimana ini bisa diatasi? Entah membatasi generalitas penuh entah bagaimana (yang tidak menyenangkan, dan dapat dengan cepat membunuh manfaat menggunakan sistem berbasis prototipe di tempat pertama), atau membuat sistem tipe jauh lebih cair dan mengungkapkan kendala daripada jenis yang tepat .

Sistem tipe berbasis kendala dengan cepat mengarah pada gagasan struktural sub-mengetik , yang dalam arti yang sangat longgar dapat dianggap sebagai setara statis "mengetik bebek". Hambatan terbesar di sini adalah bahwa sistem seperti itu jauh lebih rumit untuk diketik, dan kurang dikenal (yang berarti sedikit pekerjaan yang harus dipelajari sebelumnya).

Singkatnya: Ini mungkin, itu hanya lebih sulit untuk dilakukan daripada sistem tipe statis nominal atau sistem dinamis berdasarkan runtime metadata, dan karenanya sedikit orang yang peduli.


1

Saya percaya cara untuk mencapai bahasa berbasis prototipe yang diketik secara statis adalah dengan mendasarkan bahasa di sekitar Templat dan Konsep.

Konsep pernah menjadi fitur yang direncanakan untuk C ++ 0x. Kode generik dalam templat C ++ sudah de facto "secara statis diketik bebek". Gagasan Konsep adalah untuk dapat mengatakan beberapa hal tentang anggota yang diperlukan dan karakteristik tipe, tanpa memerlukan atau menyiratkan model pewarisan kelas yang mendasari hubungan itu (karena harus bekerja dengan kode templat yang ada yang sudah "diketik dengan bebek statis" ).

Dalam bahasa yang didasarkan dari bawah ke atas pada Templat dan Konsep, itu akan menjadi Konsep yang berbasis prototipe, dan Templat akan membebaskan Anda dari peduli tentang model kelas apa pun yang mungkin atau mungkin tidak digunakan untuk menerapkan jenis nilai.

Selain trik menggunakan kompilasi bertahap untuk memungkinkan bahasa menjadi meta-bahasa sendiri, derivasi prototipikal Konsep ini tentu tidak akan berubah begitu dibuat. Namun, keberatan yang bukan berbasis prototipe adalah herring merah. Ini hanya akan menjadi bahasa fungsional. Sebuah dinamis bahasa prototipe-dasar yang juga fungsional memiliki setidaknya dicoba .

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.