Deskripsi tantangan
Kami memiliki beberapa tantangan yang melibatkan urutan Tampilan-dan-katakan . Pengingat cepat:
- Urutan dimulai dengan
1
, - Istilah selanjutnya dari urutan ini dihasilkan dengan menyebutkan setiap kelompok digit berulang dalam istilah sebelumnya,
Jadi beberapa istilah pertama adalah:
1 "one"
11 "one one" (we look at the previous term)
21 "two ones"
1211 "one two, one one"
111221 "one one, one two, two ones"
312211 "three ones, two twos, one one"
Sekarang mari kita lakukan hal yang sama, tetapi gunakan Angka Romawi sebagai gantinya. Kita mulai dengan I
dan mengikuti aturan yang sama (alih-alih kita menerapkan aturan penghitungan angka pada karakter, jadi kita membaca IVX
sebagai one one, one five, one ten
ganti one four, one ten
atau dengan cara lain):
I "one"
II "one one"
III "two ones" = "II" + "I"
IIII "three ones" = "III" + "I"
IVI "four ones" = "IV" + "I"
IIIVII "one one, one five, one one"
IIIIIVIII "three ones, one five, two ones" = ("III" + "I") + ("I" + "V") + ("II" + "I")
Diberikan bilangan bulat positif N
, baik:
- Keluarkan
N
angka pertama dari urutan ini (juga pemisah yang masuk akal, juga["I", "II", "III", ...]
- Keluarkan
N
istilah th dari urutan ini (mungkin diindeks 0).
Ingatlah untuk membuat kode Anda sesingkat mungkin, karena ini adalah tantangan kode-golf !
EDIT: Saya percaya bahwa selalu ada satu cara standar / disukai untuk mengekspresikan bilangan bulat sebagai angka romawi, (seperti 95
-> XCV
alih-alih VC
). Beberapa konverter angka Romawi yang saya temukan online menguatkan pendapat saya. Jika ragu, gunakan konverter online , karena mendaftar semua kasus tepi yang mungkin dan aturan khusus penulisan angka Romawi bukanlah titik tantangan ini.
EDIT2: @PeterTaylor dan @GregMartin menunjukkan bahwa hanya nomor kurang atau sama untuk 5
muncul secara berurutan, sehingga Anda tidak perlu khawatir tentang ambiguitas angka Romawi (nomor 1
- 8
adalah I
, II
, III
, IV
, V
, VI
, VII
, dan VIII
)
sumber
4
/IV
/IIII
? Atau95
/XCV
/VC
? Mungkin tidak selalu ada cara unik untuk mengekspresikan bilangan bulat, tapi saya cukup yakin selalu ada yang lebih disukai (standar) - koreksi saya jika saya salah.Jawaban:
Perl, 49 byte
Termasuk +1 untuk
-p
Jalankan dengan indeks berbasis 0 pada STDIN, mis
ecce.pl
:Formula ajaib sangat ajaib.
Biasanya saya akan menggunakan
($_=//)x$'
untuk membuat kontrol loop satu byte lebih pendek, tetapi penilaian di situs ini memberikan cacat 2 sehingga berakhir 1 byte lebih lama. Pada perl yang lebih lama, Anda dapat menjatuhkan ruang sebelumnyafor
. Beberapa versi perl memaksa Anda untuk menambahkan final;
untuk menutup transliterasi. Tetapi apa yang diberikan di atas adalah kode yang berfungsi pada sistem saya.Penjelasan
Bekerja mundur dari solusi ke kode:
Transformasi string yang kita butuhkan:
Setiap penggantian berakhir dengan karakter yang diulang. Saya akan mendapatkan urutan karakter yang sama menggunakan regex
/(.)\1*/
, jadi ini bisa dilakukan dengan menambahkan$1
. Bagian sebelum->
di$&
. Dengan itu saya masih membutuhkan:Tulis
I
sebagai1
danV
sebagai 9:Dengan membagi bagian sebelum
->
dengan angka yang diulang ini menjadi:Jadi sekarang yang asli diulang
V
bukan pengecualian lagi. Jadi saya ingin ekspresi yang membuat ini terjadi:Dan ini dapat dilakukan dengan modulo 182 sederhana:
(ini bahkan bisa
IIIIII
keVI
kanan meskipun tidak diperlukan di sini)Yang tersisa adalah menginisialisasi variabel kerja untuk
1
untuk indeks 0, ulangi transformasi ini dalam satu lingkaran dan pada akhirnya ganti1
denganI
dan9
olehV
1
,9
dan182
merupakan satu-satunya kombinasi parameter yang digunakan rumus sederhana ini.sumber
Mathematica,
1139083 byteTerima kasih kepada Martin Ender untuk saran yang mengurangi panjangnya lebih dari 25%!
Memamerkan perintah tingkat tinggi di Mathematica.
Fungsi murni, mengambil argumen N dan mengeluarkan elemen ke-N dari urutan (diindeks 0) ini, sebagai daftar karakter. Sebarkan sedikit:
Bagian luar
Nest
mengulangi fungsi empat baris tengah, mulai dari{"I"}
, N kali. Baris 4 membagi daftar karakter dari angka input Romawi ke dalam run karakter seperti, menghitung setiap run denganTally
, dan menempatkan jumlah sebelum karakter yang mereka hitung. Baris 3 menjadikan penghitungan sebagai angka Romawi, lalu membagi angka Romawi tersebut ke dalam daftar karakter. TheFlatten
perintah mengurangi daftar-of-daftar keseluruhan untuk daftar satu dimensi.Ini versi awalnya:
sumber
@@@
alih-alih,/@
Anda dapat menggunakan#
dan#2
bukannya#[[1]]
dan#[[2]]
. Selain itu, daftar karakter adalah tipe string yang dapat diterima, sehingga Anda dapat menggunakannya dan tidak menggunakannyaCharacters@
.@@@
jalan pintas seperti! Adapun daftar karakter yang menjadi tipe string yang dapat diterima (yang saya setuju akan mempersingkat kodenya): adakah posting di situs ini yang dapat Anda tunjukkan kepada saya yang menggambarkan standar komunitas?Characters
utas secara otomatis sehingga Anda dapat menggunakan@
,Reverse@#&
tentu saja sama dengan polosReverse
, dalam hal ini Anda juga tidak memerlukan tanda kurung itu. Dan notasi awalan (dalam halFlatten
) tidak menyimpan apa pun jika Anda perlu menambahkan tanda kurung untuk membuatnya berfungsi. Menggabungkan semua itu:Nest[Flatten[Characters@{RomanNumeral@#,#2}&@@@Reverse@@@Tally/@Split@#]&,{"I"},#]&
CJam (
3330 byte)Demo online
Kunci kebenaran implementasi adalah teorema berikut:
Jika generasi pertama adalah
I
, tidak ada panjang run yang lebih besar dari limaLemma: jika generasi pertama adalah
I
, tidak ada string yang berisiVVV
. Bukti adalah dengan kontradiksi. Misalkan ada indeks pertaman
yangn
berisi generasi thVVV
. Jika ituVVV
rusak karena(a)V VV
konversi dari generasi sebelumnya buruk: seharusnya(a+5)V
. Jadi harusVV V(d)
, dan generasi sebelumnya terkandungVVVVV
, bertentangan dengan pilihann
.Sekarang, anggaplah ada indeks pertama
m
yangm
berisi generasi th...IIIIII...
. Perhatikan bahwa tidak boleh ada angka selainI
danV
dalam string, karena tidak ada generasi sebelumnya yang memiliki deretan sembilanI
atau sembilanV
. Paling banyak empat dariI
s berasal dari menjalankanI
s di string sebelumnya, sehingga bagian yang sesuai dari string sebelumnya harus...IIIVV...
memberi... IIII IIV ...
. KarenaVV
generasi inm-1
tidak berasal dariVVVVV
(lihat lemma),V
digit kedua harus berupa run-length digitI
, jadi dalam generasi yangm-1
kita miliki...IIIVVI...
. Dan karena kita ingin inisialI
memberiIIII
dan tidakIVI
atauVI
, didahului oleh awal string atau olehV
.Jika kita memiliki
(...V)?IIIVVI...
generasim-1
, apa yang kita miliki dalam generasim-2
? Kami sudah mengamati bahwaVV
gen.m-1
harus diurai sebagai(a)V V(I)
.Misalkan kita mengambil
a=2
:(...V)?I IIV VI...
Sebenarnya itu harus...VI IIV VI...
, meskipun pemimpin ituV
mungkin bagian dariIV
; jadi pada generasi sebelumnya kita memiliki salah satu(...V)? IIII VV IIIII...
atau(...V)? IIIII VV IIIII
. Apa pun cara kita mengalami masalah denganVVIIIII
: yang keduaV
harus berupa run-length, tetapi kemudian...VI IIII...
membutuhkan pasangan (run-length, digit) berikut dengan digit yang sama.Sehingga harus
a=1
:(...V)?II IV VI...
. Karena generasim
adalah yang pertama dengan rentang enamI
, itu harus(...V)? II IV VI...
, sehingga generasim-2
itu(...V)? I V IIIII...
....VIVIIIII...
tidak mungkin: namun kami memilih untuk menafsirkan yang keduaV
kami berakhir dengan dua pasangan (run-length, digit) berturut-turut dengan digit yang sama.Oleh karena itu generasi
m-2
harus^IVIIIII...
, diuraikan sebagai^IV IIII I(V)...
atau^IV III II(V)...
. Ini memberikan masing-masing generasim-3
sebagai^V III V ...
atau^V II VV...
.Tetapi jika kita melihat awal dari string yang dimulai dengan yang pertama dimulai
V
, kita mendapatkan sebuah siklus:dan karenanya tidak ada generasi yang memulai dengan salah satu
VIIIV
atauVIIVV
. Kita harus menyimpulkan bahwa tidak ada yang seperti itum
.Pembedahan
sumber
Python 3, 195 byte
Ada banyak byte yang terbuang pada angka romawi, jadi ada kemungkinan golf dilakukan di sana.
Terima kasih kepada @ El'endiaStarman, @ Sherlock9 dan @Shooqie
Ide itu!
sumber
for v,i in(5,"V"),(4,"IV"),(1,"I")
for v,i in(5,"V"),(4,"IV"),(1,"I"):a,x=divmod(x,v);r+=i*a
menghemat satu byte.i
(seperti padafor i in range(...)
). Saya mencoba berkecimpung denganexec
tetapi ini lolos1
dalam metode 'sub' tampaknya mengacaukan kode, saya belum dapat menemukan solusi.range
R,
110107 Bytesas.roman
dikombinasikan denganrle
membuatnya mudah. Pelingkupan pelecehan dan perilaku kucing<<-
menghemat beberapa byte.Mengambil N dari konsol. Keluaran pertama dari 2 hingga N dalam hal urutan (yang saya yakin dalam spesifikasi ...)
sumber
JavaScript (ES6), 107
Fungsi rekursif mengembalikan istilah N 0 berdasarkan
Uji
sumber
Perl 6 , 62 byte
Fungsi anonim yang menerima indeks berbasis nol.
Menggunakan fakta bahwa angka romawi lebih tinggi dari 5 tidak diperlukan, karena satu-satunya kelompok angka berulang yang dapat terjadi, adalah:
( coba online )
sumber