Pertimbangkan jenis induktif yang memiliki beberapa kejadian rekursif di lokasi bersarang, tetapi sangat positif. Sebagai contoh, pohon dengan cabang terbatas dengan node menggunakan struktur data daftar umum untuk menyimpan anak-anak.
Inductive LTree : Set := Node : list LTree -> LTree.
Cara naif mendefinisikan fungsi rekursif atas pohon-pohon ini dengan mengulangi pohon dan daftar pohon tidak bekerja. Berikut ini contoh dengan size
fungsi yang menghitung jumlah node.
Fixpoint size (t : LTree) : nat := match t with Node l => 1 + (size_l l) end
with size_l (l : list LTree) : nat := match l with
| nil => 0
| cons h r => size h + size_l r
end.
Definisi ini salah bentuk (pesan kesalahan dikutip):
Error:
Recursive definition of size_l is ill-formed.
Recursive call to size has principal argument equal to
"h" instead of "r".
Mengapa definisi ini buruk bentuknya, meskipun r
jelas-jelas merupakan bagian dari l
? Apakah ada cara untuk mendefinisikan fungsi rekursif pada struktur data seperti itu?
Jika Anda tidak lancar dalam sintaks Coq: LTree
adalah tipe induktif yang sesuai dengan tata bahasa berikut.
Kami mencoba untuk mendefinisikan size
fungsi dengan induksi lebih dari pohon dan daftar. Dalam OCaml, itu akan menjadi:
type t = Node of t list
let rec size = function Node l -> 1 + size_l l
and size_l = function [] -> 0
| h::r -> size h + size_l r
sumber
Jawaban:
Pekerjaan apa
Jika Anda mencari definisi fixpoint pada daftar di dalam definisi fixpoint pada pohon, hasilnya diketik dengan baik. Ini adalah prinsip umum ketika Anda memiliki rekursi bersarang dalam tipe induktif, yaitu ketika rekursi melalui konstruktor suka
list
.Atau jika Anda lebih suka menulis ini lebih singkat:
(Saya tidak tahu dari siapa saya mendengarnya dari awal; ini tentu saja ditemukan secara independen berkali-kali.)
Predikat rekursi umum
Secara umum, Anda dapat mendefinisikan prinsip induksi "benar"
LTree
secara manual. Prinsip induksi yang dihasilkan secara otomatisLTree_rect
menghilangkan hipotesis dalam daftar, karena generator prinsip induksi hanya memahami kejadian non-bersarang yang benar-benar positif dari tipe induktif.Mari kita tambahkan hipotesis induksi pada daftar. Untuk memenuhinya dalam panggilan rekursif, kami memanggil prinsip induksi daftar dan memberikannya prinsip induksi pohon pada pohon kecil di dalam daftar.
Mengapa
Jawaban untuk alasan terletak pada aturan yang tepat untuk menerima fungsi rekursif. Aturan-aturan ini sangat halus, karena ada keseimbangan yang rumit antara memungkinkan kasus-kasus yang kompleks (seperti yang ini, dengan rekursi bersarang dalam tipe data) dan tidak sehat. The referensi Coq panduan memperkenalkan bahasa (kalkulus konstruksi induktif, yang merupakan bahasa bukti Coq), sebagian besar dengan definisi formal yang tepat, tetapi jika Anda ingin aturan yang tepat tentang induksi dan coinduction Anda akan perlu pergi ke makalah penelitian, tentang topik ini Eduardo Giménez [1].
Fix
l
t
size
h
l
size_l
r
l
size_l
Alasan mengapa
h
secara struktural lebih kecil daripadal
menurut penerjemah Coq tidak jelas bagi saya. Sejauh yang saya mengerti dari diskusi pada daftar Coq-club [1] [2], ini adalah batasan dalam juru bahasa, yang pada prinsipnya dapat diangkat, tetapi dengan sangat hati-hati untuk menghindari memperkenalkan ketidakkonsistenan.Referensi
Cocorico, Coq wiki nonterminating: Saling Induksi
Milis Coq-Club:
Tim Pengembangan Coq. Asisten Bukti Coq: Manual Referensi . Versi 8.3 (2010). [ web ] ch. 4 .
Eduardo Giménez. Mengkodifikasi definisi yang dijaga dengan skema rekursif . Dalam Types'94: Jenis untuk Bukti dan Program , LNCS 996. Springer-Verlag, 1994. doi: 10.1007 / 3-540-60579-7_3 [ Springer ]
Eduardo Giménez. Definisi Rekursif Struktural dalam Teori Tipe . Dalam ICALP'98: Prosiding Kolokium Internasional ke 25 tentang Automata, Bahasa dan Pemrograman. Springer-Verlag, 1998. [ PDF ]
sumber
Ini jelas merupakan masalah khusus untuk Coq karena saya percaya ada cara yang lebih baik untuk mengatasinya dengan beberapa asisten bukti lainnya (Saya sedang melihat Agda)
Pada awalnya saya pikir
r
tidak dikenali secara struktural lebih kecil karena strukturnya hanya tentang definisi induktif yang saat ini ditangani olehFixpoint
: jadi ini bukanLTree
subterm walaupun itu adalahlist
subterm.Tetapi jika Anda memperluas pemrosesan daftar, maka itu berfungsi:
Atau karena fungsi bantu sudah ada di perpustakaan standar:
Sejujurnya saya tidak yakin mengapa itu diterima oleh Coq, tapi saya senang mereka.
Ada juga solusi yang bekerja lebih sering dan tidak hanya untuk daftar: mendefinisikan tipe induktif mandiri. Dalam hal ini Anda dapat mendefinisikan
size
fungsi Anda secara manual. (dengan dua fixpoints)Perhatikan bahwa jika Anda memiliki masalah untuk definisi induktif yang lebih kompleks, Anda dapat menggunakan argumen penurunan ukuran. Itu mungkin tetapi rumit untuk masalah ini (dan saya berani mengatakan untuk sebagian besar masalah)
sumber