Diberi meja, letakkan di kursi

41

Tantangan

Anda akan diberikan tabel sebagai input, digambar dengan ASCII |dan _. Tugas Anda adalah mengatur kursi di sekitarnya.

Contoh

Memasukkan:

 ____
|    |
|    |
|    |
|    |
|____|

Keluaran:

 _^_^_
<     >
|     |
<     >
|     |
<_ _ _>
  v v

Kursi-kursi itu terbuat dari <>dan v^.

Contoh lain:

Garis harus memiliki kursi sebanyak mungkin di dalamnya.

  _____
 |     |_____
 |           |
 |           |
 |           |
 |      _____|
 |_____|


  _^_^_
 <     |_^_^_
 |           >
 <           |
 |           |
 <      _ _ _>
 |_ _ _| v v
   v v

Harus ada ruang di antara setiap kursi. Dan >_^_^_<itu tidak valid, seharusnya |_^_^_|.

  _____       _____
 |     |_____|     |
 |                 |
 |                 |
 |                 |
 |      ___________|
 |_____|


  _^_^_       _^_^_
 <     |_^_^_|     >
 |                 |
 <                 >
 |                 |
 <      _ _ _ _ _ _>
 |_ _ _| v v v v v
   v v

Tidak ada kursi di bagian dalam "donat".

  _________________
 |      _____      |
 |     |     |     |
 |     |     |     |
 |     |_____|     |
 |_________________|


  _^_^_^_^_^_^_^_^_
 <      _____      >
 |     |     |     |
 <     |     |     >
 |     |_____|     |
 <_ _ _ _ _ _ _ _ _>
   v v v v v v v v

^dan vmemprioritaskan <dan >. Tidak ada kursi sendiri (harus memiliki setidaknya satu |atau _di baris).

  _________________
 |      _____      |
 |     |     |     |
 |     |     |_____|
 |     |_____
 |___________|


  _^_^_^_^_^_^_^_^_
 <      _ _ _      >
 |     | v v |     |
 <     >     <_ _ _>
 |     |_^_^_  v v
 <_ _ _ _ _ _|
   v v v v v

Ini kode golf, jadi kode terpendek menang.

Tim
sumber
2
Saya bingung, mengapa kursi-kursi tertanam di meja dari samping?
Pengoptimal
Jika saya ingat dengan benar, pos kotak pasir asli Anda memiliki ruang antara garis tabel vertikal dan garis kursi. Sama seperti ada sedikit ruang antara garis meja horizontal dan kursi.
Pengoptimal
1
sepertinya kursi ditempatkan dengan 1 jarak satu sama lain, tetapi input di sekitarnya tidak dapat dibagi 2. bagaimana program harus mulai meletakkan kursi. Searah jarum jam atau anti-jam? dari sudut kanan atas, sudut kiri atas dll?
1
juga saya pikir ada masalah dalam sampel ketiga - ada ruang tambahan antara kursi "atas" kedua dan ketiga - dan juga dalam contoh terakhir, sudut kanan bawah
1
Kasus uji pertama tampaknya rusak. Inputnya hanya 4 lebar dan outputnya 5.
Wheat Wizard

Jawaban:

34

Python 2, 1033 1007 924 879 829 787 713 699 692 691 688 687 672 670 664 659 654 648 643 642 630 625 623 620 570 560 554 545 518 514 513 510 505 492 476 454 451 443 bytes

6 byte disimpan berkat Riley

6 byte disimpan berkat Adnan

Karena pertanyaan ini sudah berusia lebih dari satu tahun dan masih belum memiliki jawaban, saya pikir saya akan mencobanya.

n,i,o,u="\nI _";R=lambda x:range(1,x-1)
b=open(i).read()
s=b.split(n)
z=max(map(len,s))+3
a=[list(i+x.ljust(z,i))for x in[i]+s+[i]]
for x in R(len(a))*len(b):
 A=a[x];B=a[x+1];C=a[x-1]
 for y in R(z):
    D=A[y-1:y+2];k=B[y];j=A[y+1]
    if(i in[C[y],k]+D+(k==u)*B[y-1:y+2]or"V"==j)&(A[y]==o):A[y]=i
    if"|"==A[y]==C[y]:A[y]={i:"|",j:">",A[y-1]:"<"}[i]
    if[u]*3==D:A[y],B[y]={i:u+k,C[y]:"^"+k,k:" V"}[i]
print n.join(`y`[2::5]for y in a).replace(i,o)

Cobalah online!

Program membaca tabel nama file Idan mencetak tabel dengan kursinya std::out. Saya tidak yakin tentang banyak kasus tepi jadi saya mengambil penilaian terbaik saya (apa pun yang paling sedikit usaha) tetapi tampaknya melewati semua kasus uji. Beberapa output tidak sama persis tetapi mereka semua memiliki jumlah kursi yang sama.

Penjelasan

Baris pertama cukup membuat beberapa definisi yang akan menyelamatkan kita byte di masa depan:

(Saya akan membongkar makro ini untuk dibaca di baris mendatang)

n,i,o="\nI ";R=lambda x:range(1,x-1)

Kemudian kita akan membuka file bernama Ikarena kita sudah memiliki variabel yang merupakan kependekan dari itu sehingga menghemat beberapa byte.

b=open("I").read().split("\n")

Kami membagi sepanjang baris baru untuk membuat daftar string (Baris gambar)

s=b.split(n)

Saya kemudian menemukan panjang garis terpanjang sehingga saya bisa mengisi semua garis dengan panjang itu. (Saya juga menambahkan 3 karena kami membutuhkan sedikit tambahan tambahan)

 z=max(map(len,s))+3

Kemudian kami melakukan padding yang sebenarnya dan membuat batas Ikarakter di sekitar tepi. Ini karena kita perlu memberi tahu perbedaan antara bagian dalam dan bagian luar bentuk nanti. Kami juga akan mengubah tipe data dari daftar string ke daftar daftar karakter (panjang 1 string).

a=[list("I"+x.ljust(z,"I"))for x in["I"]+s+["I"]]

Baris berikutnya hanyalah definisi penghematan byte lain.

(Saya juga akan membongkar yang ini)

B=R(len(a))

Sekarang kami ingin menyebarkan Ikarakter ke mana saja di luar bentuk. Kita dapat melakukan ini dengan otomat pseudo-seluler. Masing I- masing akan menyebar ke karakter yang berdekatan . Kita dapat mengulang sampai otomat stabil tetapi ini tidak dapat mengambil lebih banyak iterasi daripada karakter sehingga kita hanya mengulang setiap karakter dalam b(input asli)

for _ in b:

Untuk setiap iterasi kami ingin melewati setiap karakter dalam daftar 2D (tidak termasuk padding terluar)

 for x in range(1,len(a)-1):
    A=a[x]  #<--Another definition I will fill in for clarity
    for y in range(1,z-1):

Untuk setiap posisi kami menjalankan kode berikut:

if("I" in[a[x+1][y],a[x-1][y]]+a[x][y-1:y+2])&(a[x][y]==" "):a[x][y]=" "

Mari kita hancurkan ini.

Kami memiliki if dengan dua kondisi yang dipisahkan oleh &(bitwise and)

Yang pertama hanya memeriksa apakah ada Idi salah satu sel yang berdekatan dan yang kedua hanya memeriksa apakah sel saat ini adalah a " ". Jika kami melewati kondisi tersebut, kami menetapkan sel saat ini menjadi I.


Sekarang kita telah menentukan bagian luar dan dalam bentuknya, kita dapat mulai menempatkan kursi di sekeliling meja.

Sekali lagi kita mengulang semua sel (dan mengatur beberapa singkatan lagi)

for x in range(1,len(a)-1):
 A=a[x]
 for y in range(1,z-1):
        k=a[x+1][y]

Sekarang inilah bagian favorit saya. Jika Anda berjalan dengan susah payah melalui golf yang membosankan, sebagian besar berbasis definisi, sejauh ini saya akan menghadiahi Anda dengan berita gembira yang bagus tentang bermain golf pintar (jika saya mengatakannya sendiri).

Sedikit latar belakang python:

Dalam Python jika Anda mencoba untuk menetapkan kunci kamus dua kali itu menandakan yang terakhir. Sebagai contoh

>>> {1:"a",1:"b"}[1]
'b'

Kami akan menyalahgunakan properti ini untuk menetapkan sel saat ini ke karakter tertentu.

Kondisi pertama adalah

if["_"]*3==a[x][y-1:y+2]:a[x][y],a[x+1][y]={"I":"_"+a[x+1][y],a[x-1][y]:"^ ",a[x+1][y]:" V"}["I"]

Jika sel berada di tengah-tengah tepi 3 _karakter, kami akan menugaskan kembali sel saat ini dan sel di bawahnya. Kami akan menetapkannya ke hasil pengindeksan kamus yang kelebihan beban oleh I. Kami pertama-tama menetapkan default kami dengan pasangan "I":"_"+a[x+1][y]ini artinya jika tidak ada perubahan kami akan menetapkan dua sel kembali ke nilai aslinya. Selanjutnya kita tambahkan pasangan a[x-1][y]:"^ ". Ini tidak akan melakukan apa pun (penting) kecuali sel di atas yang sekarang ( a[x-1][y]) diisi dengan I. Jika ada Idi dalamnya, maka akan menimpa default yang memberitahu kita untuk menempatkan kursi di sel saat ini. Selanjutnya kita beralih ke sel di bawah sel saat ini jika sel itu Ikita timpa lagi untuk menempatkan kursi menghadap ke atas di bawah tempat saat ini.

Kondisi selanjutnya sedikit lebih sederhana

if"|"==a[x][y]==a[x-1][y]:a[x][y]={"I":"|",A[y+1]:">",A[y-1]:"<"}["I"]   

Kami memeriksa apakah sel saat ini dan sel di atas keduanya |. Jika demikian, kami membuat kamus.

Pasangan pertama dalam kamus "I":"|"menetapkan standar. Karena kita akan mengakses kunci Ijika Itidak dipindahkan maka akan kembali ke default |(karakter sudah ada) dan tidak melakukan apa-apa.

Kita menambahkan dua kunci. A[y+1]:">",A[y-1]:"<"Jika salah satu dari dua sel di kiri dan kanan, Imaka itu akan menugaskan kembali sel saat ini ke kursi yang menunjuk ke arah luar.


Sekarang kita hanya perlu output. Namun kita tidak bisa hanya mencetak, ada beberapa hal yang harus kita lakukan terlebih dahulu. Kami harus mengonversi kembali ke string dan menghapus semua yang Ikami buat. Ini dilakukan dalam satu baris.

print "\n".join(`y`[2::5]for y in a).replace("I"," ")
Wisaya Gandum
sumber
Tidak bisakah Anda menggunakan spasi untuk indentasi tingkat pertama, tab untuk dua, tab dan spasi untuk tiga? Itu akan menghemat beberapa byte.
Riley
3
Ini mungkin jawaban paling golf.
Magic Gurita Guci
2
Apakah i,o="I "alih-alih i="I";o=" "bekerja?
Adnan
1
@ErikGolfer エ リ ッ ク ゴ ル フ ァ ー Menghasilkan nbiaya 4 byte dan menyelamatkan saya 6. Meskipun saya tidak menggunakannya sering menghemat 2 byte.
Wheat Wizard
1
@ Pietu1998 Terima kasih telah menunjukkan itu. Saya memperbaiki masalah ini
Wheat Wizard