Tugas Anda: menghasilkan kepingan salju Koch ke kedalaman n. Anda tidak perlu membuat kepingan salju Koch lengkap, hanya satu sisi dari segitiga awal. Wikipedia di Koch flakes: https://en.wikipedia.org/wiki/Koch_snowflake .
Aturan:
- Program harus menghasilkan satu sisi kepingan salju Koch hingga ke kedalaman n.
- Keluaran harus ASCII.
- Anda dapat menghasilkan seluruh kepingan salju; ini tidak wajib.
- Aturan standar untuk input / output dan celah dan hal-hal berlaku.
- Spasi tidak masalah, selama semua karakter berada di tempat yang tepat relatif satu sama lain.
- Kode terpendek menang!
Kasus uji:
n = 0:
__
n = 1:
__/\__
n = 2:
__/\__
\ /
__/\__/ \__/\__
n = 3:
__/\__
\ /
__/\__/ \__/\__
\ /
/_ _\
\ /
__/\__ __/ \__ __/\__
\ / \ / \ /
__/\__/ \__/\__/ \__/\__/ \__/\__
Saya harap ini masuk akal. Perhatikan bahwa dalam setiap kasus uji, fraktal dapat dibagi menjadi tiga bagian dengan panjang yang sama. Perhatikan juga bahwa lebar setiap kepingan salju tiga kali lebih lebar dari kepingan salju generasi sebelumnya.
__/\__
dengan dua garis bawah, yang membuat setiap iterasi secara konsisten 3 kali lebih besar dari yang sebelumnya. Menggunakan hanya satu garis bawah nampaknya memberikan kontradiksi yang mulai menjadi sangat canggung dalam n = 3. Misalnya bagian luar memiliki lebar 12 sedangkan bagian tengah hanya memiliki lebar 10, sebagai akibat dari/_
dan_\
yang terlalu sempit. Dan bahkan sebelum itu Anda telah_
memperluas dua kali lebar/
dan\
./_
dan_\
adalah satu-satunya bagian yang benar-benar fatal - garis bawah harus dilalui, karena mereka harus berada pada posisi yang sama dengan/
dan\
. Setelah selesai, hal-hal dapat diperluas 3 kali dari n = 1 dan seterusnya (tetapi n = 0 tidak cocok.)Jawaban:
Haskell ,
308300299 byteSuntingan:
zipWith(+)
kezipWith(-)
dan menyesuaikan pengkodean dan offset menyingkirkan setiap tanda negasi.#
untuk dihapus dengan menggunakanr=reverse
alih-alih pencocokan pola langsung.zipWith(-)
.o=[0,0]
untuk mempersingkat konstanta daftar.?
.Cobalah online! (Sedihnya, apa pun yang lebih besar dari n = 3 dibungkus dengan mengerikan dan tidak dapat dibaca, tetapi Anda dapat menyalinnya ke program lain untuk melihatnya.)
Variasi
[6]
menjadi[6,4,4]
, Anda mendapatkan kepingan salju keseluruhan. Cobalah online!,3..gcd 3x
, Anda mendapatkan kurva dalam gaya yang awalnya diberikan pertanyaan ini. Cobalah online!Bagaimana itu bekerja
k
adalah fungsi utama, dibutuhkanInt
n
dan mengembalikan aString
.iterate(>>=(:[1,4,1]))[6]
menghasilkan daftar tak terbatas yang mengandung, untuk setiap n, belokan antara garis berurutan dalam iterasi kurva, gaya grafis turtle, sebagai angka yang secara nominal antara0
dan5
. Setiap iterasi hanya yang sebelumnya dengan belokan1,4,1
disisipkan. Satu-satunya alasan sublists memulai dengan6
alih - alih0
adalah untuk membuatgcd
trik dalamf
bekerja dengan menghindarif 0
.scanl1(+)
mengubah belokan menjadi arah "absolut", hingga modulo 6. A0
berarti ke kanan, maka setiap angka yang lebih tinggi adalah 60 derajat berlawanan arah jarum jam dari sebelumnya. (Yah, itu akan menjadi 60 derajat jika ini adalah gambar yang tepat daripada ASCII.)f
mengubah arah absolut menjadi daftar (karakter, penyandian offset) pasangan yang menyandikan karakter mana yang akan ditambahkan ke kurva (untuk arah horizontal, ia menghasilkan dua pasangan, jika tidak satu), dan bagaimana posisi relatif berubah.#
iterates Operator melalui daftar sebelumnya (karakter, offset encoding) pasang, menghasilkan sebenarnya (koordinat, karakter) pasang._/\
nominal mewakili garis yang ditarik dari sudut mulai melalui sel persegi panjang ke sudut akhir yang berbeda.[y,x]
, atas ke bawah, kiri ke kanan, sehingga mereka mengurutkan dalam urutan yang ingin kita cetak. Kolom berbasis 1. Daftar digunakan sebagai pengganti tupel untuk aritmatika vektor yang lebih pendek(&)=zipWith(-)
.[y,x]
dengan sel di kiri atas. Ini memastikan bahwa semua offset dari sudut ke sel-sel di sekitarnya tidak negatif, menghindari konstanta negatif.[y1,x1,x2,y2]
tempat[y1,x1]
offset koordinat dari sudut awal ke sel karakter dan[y2,x2]
merupakan offset dari sudut ujung ke sel karakter. Ini berarti:3
..5
hanyalah kebalikan dari daftar untuk0
..2
, yang memungkinkan mereka dihasilkan[id,r]<*>
.(&)=zipWith(-)
daftar pengodean atau kebalikannya.?
, yang menghasilkan finalString
dari mereka.x?l@(([_,w],c):r)
x
adalah koordinat x dari karakter sebelumnya yang ditunjukkan pada baris ini, atau0
jika pada awal baris;l
adalah seluruh daftar saat ini,w
adalah koordinat x dari karakter berikutnya yang akan ditambahkan,c
adalah karakter, danr
merupakan daftar yang tersisa.\
dan/
, sehingga akan diurutkan terakhir jika tumpang tindih dengan karakter lain di posisi yang sama. Jadi garis bawah yang berlebihan terdeteksi dengan memeriksa bahwa koordinat x telah diulang.sumber