Q, 47 Bytes
m:{*/1_-':|(0<){y-x x bin y}[*+60(|+\)\1 0]\x}
Uji
+(i;m'i:1 2 3 4 5 6 7 8 9 42 1000 12345)
membacanya sebagai pasangan (i, map (m, i)), di mana m adalah fungsi penghitungan dan i argumen yang berbeda
menulis
1 1
2 2
3 3
4 3
5 5
6 5
7 10
8 8
9 8
42 272
1000 12831
12345 138481852236
Penjelasan
n funtion\arg
menerapkan fungsi (fungsi (fungsi (... fungsi (argumen)))) n kali (secara internal menggunakan rekursi tal), dan mengembalikan urutan hasil. Kami menghitung 60 item pertama dari seri fibonnaci sebagai *+60(|+\)\1 0
. Dalam hal ini fungsinya adalah ( | +): + \ diterapkan pada urutan menghitung jumlah parsial (ex + \ 1 2 3 adalah 1 3 6), dan | membalikkan seq. Jadi setiap 'iterasi' kita menghitung jumlah parsial dari dua nomor fibonacci sebelumnya dan mengembalikan parsial jumlah terbalik, 60(|+\)\1 0
menghasilkan urutan 1 0, 1 1, 2 1, 3 2, 5 3, 8 5, 13 8, 21 13, ... *+
diterapkan pada hasil ini membalik (traspose) dan mengambil yang pertama. Hasil adalah urutan 1 1 2 3 5 8 13 21 34 55 ..
(cond)function\args
berlaku function (function (.. function (args))) sementara cond true, dan mengembalikan urutan hasil parsial
function[arg]
diterapkan pada fungsi lebih dari satu argumen membuat proyeksi (aplikasi sebagian)
Kita bisa memberi nama pada args, tetapi nama implisitnya adalah x, y, z
{y-x x bin y}[*+60(|+\)\1 0]
mendeklarasikan lambda dengan args x, y dengan proyeksi parsial (arg x adalah deret fibonacci, dihitung sebagai * + 60 (| +) \ 1 0). x mewakili nilai fibonacci, dan y angka untuk diproses. Pencarian biner (bin) digunakan untuk mencari indeks angka fibonacci yang lebih besar <= y ( x bin y
), dan mengurangi nilai yang sesuai dari x.
Untuk menghitung produk dari resuls parsial, kami membalikkannya dan menghitung perbedaan masing-masing pasangan ( -':|
), jatuhkan yang pertama ( 1_
karena 0) dan dikalikan ( */
).
Jika kita tertarik pada jumlah akumulasi kodenya sama, tetapi dengan +/
alih - alih */
. Kami juga dapat menggunakan operator diadik lain alih-alih + atau *
Tentang efisiensi eksekusi
Saya tahu bahwa dalam kontes ini efisiensi tidak menjadi masalah. Tetapi dalam masalah ini kita dapat berkisar dari biaya linier ke biaya eksponensial, jadi saya ingin tahu tentang hal itu.
Saya mengembangkan versi kedua (panjang 48 Bytes tidak termasuk komentar) dan menguji ulang baterai 1000 kali pada kedua versi.
f:*+60(|+\)\1 0;m:{*/1_-':|(0<){x-f f bin x}\x} /new version
waktu eksekusi adalah: versi asli 0'212 seg, versi baru 0'037 seg
Versi asli menghitung seri fibbonaci sekali per aplikasi fungsi; versi baru menghitung fibonacci hanya satu.
Dalam kedua kasus perhitungan seri fibonacci menggunakan rekursi ekor
2
dapat didekomposisi sebagai-1 + 3
. Pernyataan yang benar dari teorema Zeckendorf adalah bahwa angka Fibonacci positif dapat secara unik diuraikan sebagai jumlah angka Fibonacci non-berturut-turut dengan indeks positif.