Masalah gadai yang hilang

14

Masalah gadai yang hilang

Setelah permainan catur berakhir, pion yang masih hidup tertinggal di belakang garis musuh. mari kita bantu dia menemukan jalan pulang terpendek.

Masalah aslinya menggambarkan papan "catur" nXn, dan fungsi f: {1,..,n-1}X{1,..,n}X{-1,0,1} => R+bobot. tujuannya adalah untuk menemukan jalur terbaik dari beberapa kotak di garis buttom, ke kotak lainnya di baris atas, di mana langkah yang mungkin adalah: kiri-atas, atas, kanan-atas, dan Anda tidak boleh keluar dari papan.

Masalahnya relatif mudah diselesaikan di O (n ^ 2) menggunakan pemrograman dinamis, tapi ini codegolf, dan kami tidak peduli tentang hal-hal yang tidak berguna seperti menjalankan kompleksitas waktu ...

Masalah

input: array 3-dimensi (atau koleksi lain pilihan Anda, diterima melalui stdin, atau sebagai argumen fungsi), yang sesuai dengan papan catur biasa, persis dalam ukuran: 7X8X3 (#linePasses X #rowSize X #movesPerPass) yang berisi bilangan bulat non-negatif. biaya pergerakan dari beberapa posisi di (i,j)mana iindeks baris, dan jindeks kolom, adalah:

  • a[i][j][0]untuk biaya perjalanan up-kiri untuk persegi (i+1,j-1), atau grafis: \.
  • a[i][j][1]untuk biaya untuk perjalanan hingga persegi (i+1,j), atau grafis: |.
  • a[i][j][2]untuk biaya perjalanan up-kanan untuk persegi (i+1,j+1), atau grafis: /.

Anda mungkin menganggap itu tidak akan berisi jalur yang jumlahnya lebih besar dari MAX_INT.

output: output ascii 8X8 yang menunjukkan jalur terbaik (terpendek, yaitu jumlah bobot minimum) (jika ada lebih dari 1 hasil optimal, Anda dapat menunjukkan jalur sewenang-wenang pilihan Anda). jalan digambar dari bawah ke atas, di mana di setiap baris, karakter yang sesuai dengan posisi pion di jalan, adalah yang akan dibuatnya. mis. jika pion akan bergerak ke kiri dari kolom 3 (ke kolom 2), Anda harus menggambar:

#?######
##\#####

di mana ?harus diganti dengan langkah selanjutnya. posisi akhir perlu diambil sebagai X.

Contohnya

memasukkan:

[
  [[1,1,1],[1,1,1],[0,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]],
  [[1,1,1],[1,0,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]],
  [[1,1,1],[1,1,0],[1,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]],
  [[1,1,1],[1,1,1],[1,1,0],[1,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]],
  [[1,1,1],[1,1,1],[1,1,1],[1,0,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]],
  [[1,1,1],[1,1,1],[1,1,1],[1,0,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]],
  [[1,1,1],[1,1,1],[1,1,1],[0,1,1],[1,1,1],[1,1,1],[1,1,1],[1,1,1]]
]

keluaran:

##X#####
###\####
###|####
###|####
##/#####
#/######
#|######
##\#####

memasukkan:

[
  [[41,27,38],[12,83,32],[50,53,35],[46,32,26],[55,89,82],[75,30,87],[2,11,64],[8,55,22]],
  [[56,21,0],[83,25,38],[43,75,63],[56,60,77],[68,55,89],[99,48,67],[94,30,9],[62,62,58]],
  [[23,18,40],[24,47,61],[96,45,72],[71,6,48],[75,63,98],[93,56,51],[23,31,30],[49,34,99]],
  [[20,47,42],[62,79,72],[32,28,44],[68,61,55],[62,39,57],[4,17,49],[97,85,6],[91,18,12]],
  [[51,50,11],[32,39,56],[12,82,23],[33,88,87],[60,55,22],[29,78,14],[70,11,42],[63,94,67]],
  [[75,64,60],[27,79,86],[70,72,56],[55,45,32],[95,67,12],[87,93,98],[81,36,53],[38,22,93]],
  [[31,80,50],[77,71,22],[59,46,86],[64,71,53],[41,19,95],[62,71,22],[92,80,41],[26,74,29]]
]

keluaran:

######X#
#####/##
####/###
#####\##
#####|##
######\#
######|#
#######\

ini , jadi kode terpendek menang.

bermain adil. tidak ada celah ...

EDIT:

Iv'e menulis solusi lurus ke depan yang tidak di-golf di scala yang bisa Anda lihat. Ada juga situs yang dapat Anda mainkan dengan kode scala on-line: scalakata (cukup salin & tempel inti ke scalakata, dan tekan tombol putar)

gilad hoch
sumber

Jawaban:

5

T: 199 Bytes

f:{m::x;n::{@/[+/-1 0 1_\:/:(x;m[y;;|!3]);0 2;(0W,),{x,0W}]};i:*<*|r:{&/n[x;y]}\[8#0;!7];  s:{-1+{*<x}'+n[y;z]}\[();(,8#0),-1_r;!7];j:i,{x+y x}\[i;|s];-1(@[8#"#";;:;]'[j;"X","/|\\"1+s'[|!7;-1_j]]);}

CATATAN

  • Q interpreter (kx.com) gratis untuk penggunaan non-komersial (versi untuk Windows, Linux, Mac)
  • Solusi ini menggunakan inti dari Q (bernama internal k4), jadi kita memerlukan file skrip dengan ekstensi k, atau interpreter interaktif dalam mode k (\ perintah pada prompt pertama). Sebaliknya, versi bahasa 'verbose' (terbaca) memerlukan skrip dengan ekstensi q, dan merupakan mode default di interpreter interaktif.

UJI

f ((1 1 1; 1 1 1; 0 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1)
   (1 1 1; 1 0 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1)
   (1 1 1; 1 1 0; 1 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1)
   (1 1 1; 1 1 1; 1 1 0; 1 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1)
   (1 1 1; 1 1 1; 1 1 1; 1 0 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1)
   (1 1 1; 1 1 1; 1 1 1; 1 0 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1)
   (1 1 1; 1 1 1; 1 1 1; 0 1 1; 1 1 1; 1 1 1; 1 1 1; 1 1 1))

##X#####
###\####
###|####
###|####
##/#####
#/######
#|######
##\#####

f ((41 27 38; 12 83 32; 50 53 35; 46 32 26; 55 89 82; 75 30 87;  2 11 64;  8 55 22)
   (56 21  0; 83 25 38; 43 75 63; 56 60 77; 68 55 89; 99 48 67; 94 30  9; 62 62 58)
   (23 18 40; 24 47 61; 96 45 72; 71  6 48; 75 63 98; 93 56 51; 23 31 30; 49 34 99)
   (20 47 42; 62 79 72; 32 28 44; 68 61 55; 62 39 57;  4 17 49; 97 85  6; 91 18 12)
   (51 50 11; 32 39 56; 12 82 23; 33 88 87; 60 55 22; 29 78 14; 70 11 42; 63 94 67)
   (75 64 60; 27 79 86; 70 72 56; 55 45 32; 95 67 12; 87 93 98; 81 36 53; 38 22 93)
   (31 80 50; 77 71 22; 59 46 86; 64 71 53; 41 19 95; 62 71 22; 92 80 41; 26 74 29))

######X#
#####/##
####/###
#####\##
######\#
######|#
######|#
#######\

PENJELASAN

Untuk tujuan ilustrasi, kami menganggap tes kedua (matriks ((41 27 38; 12 83 32; ....)

Kami mentransformasikan matriks asli (m pada level kode): alih-alih matriz orginimal dengan triplet untuk setiap koordinat, kami mendefinisikan matriks untuk perpindahan kiri, atas, dan kanan. Matriks kiri berisi 7x7 nilai (kami drop kolom pertama), Up matrix 7x8, dan matriks kanan 7x7 (kami cari kolom terakhir).

left                           up                         right
12 50 46 55 75 2  8       27 83 53 32 89 30 11 55     38 32 35 26 82 87 64
83 43 56 68 99 94 62      21 25 75 60 55 48 30 62     0  38 63 77 89 67 9 
24 96 71 75 93 23 49      18 47 45 6  63 56 31 34     40 61 72 48 98 51 30
62 32 68 62 4  97 91      47 79 28 61 39 17 85 18     42 72 44 55 57 49 6 
32 12 33 60 29 70 63      50 39 82 88 55 78 11 94     11 56 23 87 22 14 42
27 70 55 95 87 81 38      64 79 72 45 67 93 36 22     60 86 56 32 12 98 53
77 59 64 41 62 92 26      80 71 46 71 19 71 80 74     50 22 86 53 95 22 41

Untuk menghitung posisi akhir kita perlu mengevaluasi jalur biaya minimum. Kami mengasumsikan biaya awal 0 0 0 0 0 0 0 0 (biaya untuk tiba di setiap kolom pada baris pertama), dan diganti dengan setiap baris berikutnya. Di setiap kolom i, kami menghitung tiga nilai:

  • biaya nilai i +1 sebelumnya ditambah kiri [i +1]. Kami menjatuhkan komponen biaya pertama (menggeser dan mengubah kolom untuk ditambahkan) dan menjumlahkan komponen ke komponen

  • biaya nilai i sebelumnya ditambah [i]. Kami menjumlahkan komponen ke komponen

  • biaya nilai i-1 sebelumnya ditambah hak [i-1]. Kami menjatuhkan komponen biaya terakhir (menggeser dan mengganti kolom untuk ditambahkan) dan menjumlahkan komponen ke komponen

Untuk menghitung minimum, kami menyelesaikan penambahan biaya tak terbatas yang bergantung pada tak terbatas dan biaya tak terbatas: dengan 3 vektor dari delapan komponen, hitung komponen minimum untuk komponen. Nilai yang dihasilkan adalah biaya dasar untuk iterasi baru

Untuk iterasi pertama kita mendapatkan nilai (0W tidak terbatas dalam Q)

0W 12 50 46 55 75 2  8
27 83 53 32 89 30 11 55
38 32 35 26 82 87 64 0W

dan menghitung minimum setiap kolom

27 12 35 26 55 30 2 8

Setelah semua iterasi, kami memiliki biaya minimum untuk tiba di setiap kotak (dengan asumsi baris 0 di atas, 7 di bawah). Kami hanya tertarik pada kolom terakhir, tetapi saya menggambar semua hasil antara untuk tujuan ilustratif

0   0   0   0   0   0   0   0
27  12  35  26  55  30  2   8
27  37  78  82  110 78  11  70
45  61  123 88  173 129 34  104
87  123 151 143 212 133 40  122
98  155 163 176 234 147 51  185
158 182 219 208 246 234 87  207
208 204 265 261 265 256 128 233

Sekarang kami menemukan nilai minimum di baris terakhir (128, di kolom 6). Itulah akhir dari jalur (karakter X di ouput).

Kami mengulangi perhitungan biaya lagi, tetapi sekarang kami memberi anotasi arah dari kami memperoleh setiap minimum (yang dari 3 nilai yang digunakan untuk menghitung minimum adalah nilai yang dipilih).

\|/|\///
\\\\\/|/
\\\|//|/
\\|\//|/
\\|//|\/
\\//|\|/
\|/|/|\/

Kami membalikkan baris, meletakkan 'X' di pos 6, dan hanya mempertahankan jalur yang berakhir di kolom 6 (yang lain diganti dengan #)

######X#
#####/##
####/###
#####\##
######\#
######|#
######|#
#######\
J. Sendra
sumber
Iv'e tidak pernah mendengar tentang Q, tapi terima kasih atas tanggapan terperinci seperti itu :)
gilad hoch