Tulis semua karakter Braille yang mungkin

13

Teka-teki menarik datang kepada saya sambil melihat tombol lift pagi ini.

Anda harus membuat daftar semua pola Braille yang sesuai dengan kisi 2x3. Gunakan hash #untuk menunjukkan benjolan dan tanda hubung -untuk menunjukkan daerah datar.

Sampel keluaran yang diharapkan:

#-
--
--

##
--
--

#-
#-
--

(and so on...)

Aturan:

  • Program Anda harus memisahkan setiap pola dengan setidaknya satu karakter atau garis.
  • Pola dapat dihasilkan dalam urutan apa pun.
  • Semua pola, apa pun alfabet Braille yang sebenarnya digunakan, harus dibuat. Pola yang benar-benar kosong adalah opsional.
  • Hanya pola benjolan unik yang harus dihasilkan. Pola berikut ini dianggap sama karena benjolan berada dalam pengaturan yang identik. Dalam kasus ini, gunakan pola yang paling dekat dengan sudut kiri atas (mis. Opsi pertama dalam contoh ini.)
#-  -#  --  --
#-  -#  #-  -#
--  --  #-  -#

Bonus poin jika Anda dapat membuatnya bekerja untuk setiap x oleh y kotak berukuran. ( EDIT: Dalam batas wajar. Hingga 4x4 sudah cukup untuk bukti konsep.)

Membaca artikel wiki, tampaknya ada 45 pola (termasuk yang kosong) yang memenuhi aturan teka-teki ini.

Makanan Tangan
sumber
Ini tidak masuk hitungan, tapi sangat dekat. Untuk xx ykisi Anda menghasilkan 2^(xy)angka pertama dan memfilter angka yang menutupi 0 terhadap 2^x - 1atau (2^(xy+1) - 1)/(2^y - 1).
Peter Taylor

Jawaban:

6

GolfScript, 34 32 karakter

44,{84+2base(;{'-#'=}/@\n.}%2/n*

Ternyata bahwa ada yang solusi yang lebih pendek daripada hanya menghasilkan semua 64 pola dan menyaring yang buruk. Bahkan, dengan memetakan bit ke posisi grid dengan tepat, dimungkinkan untuk memetakan semua pola yang valid (tidak kosong) ke rentang angka yang berurutan, seperti yang dilakukan program ini.

Secara khusus, pemetaan yang saya gunakan adalah:

5 4
3 1
2 0

di mana angka-angka menunjukkan posisi bit (mulai dari bit paling signifikan 0) dipetakan ke posisi itu di grid. Dengan pemetaan ini, kisi-kisi yang valid sesuai dengan angka 20 hingga 63 inklusif.

Ini hampir sama dengan pemetaan yang jelas diperoleh dengan menuliskan angka 6-bit dalam biner dan menambahkan jeda baris antara setiap bit kedua, kecuali bahwa bit 1dan 2ditukar - dan memang, itulah cara program saya menghitungnya. (Saya juga menambahkan 64 ke angka-angka sebelum mengubahnya menjadi biner, dan kemudian menghapus bit ekstra tinggi; itu hanya untuk memasukkan angka menjadi 6 bit, karena GolfScript's basetidak akan mengembalikan nol yang memimpin.)

Ps. Demo online di sini. (Server tampaknya kelebihan beban akhir-akhir ini; jika Anda mendapatkan batas waktu, coba lagi atau unduh juru bahasa dan mengujinya secara lokal.)

Sunting: Berhasil menyimpan dua karakter dengan menghindari pembangunan array yang tidak perlu dan dumping. Fiuh!

Ilmari Karonen
sumber
2
Apakah Anda keberatan menambahkan beberapa detail? Saya tertarik untuk melihat bagaimana Anda mendefinisikan pemetaan ini.
ardnew
@ardnew: Selesai, lihat di atas.
Ilmari Karonen
Saya pikir ini akan mengubah banyak jawaban orang. :-)
Hand-E-Food
3

Mathematica 97

Grid /@ Cases[(#~Partition~2 & /@ Tuples[{"#", "-"}, 6]), x_ /; 
         x[[All, 1]] != {"-", "-", "-"} && x[[1]] != {"-", "-"}]

braille


Kosong tidak termasuk:

Length[%]

44

NB! = Adalah karakter tunggal dalam Mathematica.

DavidC
sumber
3

C # - 205

class C{static void Main(){var s="---##-##";Action<int,int>W=(i,m)=>{Console.WriteLine(s.Substring((i>>m&3)*2,2));};for(int i=0;i<64;++i){if((i&3)>0&&(i&42)>0){W(i,0);W(i,2);W(i,4);Console.WriteLine();}}}}

Versi yang dapat dibaca:

class C
{
    static void Main()
    {
        var s = "---##-##"; // all two-bit combinations
        // a function to write one two-bit pattern (one line of a Braille character)
        Action<int,int> W = (i,m) => { Console.WriteLine(s.Substring(((i >> m) & 3) * 2, 2)); };
        // for all possible 6-bit combinations (all possible Braille characters)
        for(int i = 0; i < 64; ++i)
        {
            // filter out forbidden (non-unique) characters
            if ((i & 3) > 0 && (i & 42) > 0)
            {
                // write three rows of the Braille character and an empty line
                W(i,0);
                W(i,2);
                W(i,4);
                Console.WriteLine();
            }
        }
    }
}
Mormegil
sumber
3

Perl, 71 67 65 karakter

y/10/#-/,s/../$&
/g,/^#/m&&print
for map{sprintf"%06b
",$_}18..63

Ubah int menjadi biner, lakukan transliterasi, dan tambahkan baris baru setelah setiap dua karakter. The /^#/muji menghilangkan dua pola (20 dan 21) yang tidak memiliki benjolan dibesarkan di kolom paling kiri.

Solusi umum, 150 106 103 100 char

Baca xdan ydari argumen baris perintah. Baris baru sangat penting

y/01/-#/,s/.{$x}/$&
/g,/^#/m*/^.*#/&&print
for map{sprintf"%0*b
",$x*$y,$_-1}1..1<<($y=pop)*($x=pop)

Iterasi lebih dari 0,2 xy seperti sebelumnya, konversi setiap int ke biner, gantikan -dan #untuk 0dan 1, dan masukkan baris baru setelah setiap $xkarakter.

/^#/mmenguji bahwa ada tonjolan yang muncul di kolom paling kiri, dan /^.*#/mengetes adanya tonjolan di baris paling atas. Hanya pola yang lulus kedua tes yang dicetak.

massa
sumber
Bagaimana cara akun ini untuk kombinasi yang tidak valid?
scleaver
Karena loop tidak termasuk pola untuk 1..17, 20, dan 21.
mob
2

Python, 120 118 113 95 118

for j in range(256):
    if j/4&48and j/4&42:print''.join('_#'[int(c)]for c in bin(j/4)[2:].rjust(6,'0'))[j%4*2:j%4*2+2]

Sunting: menggunakan saran Winston Ewert dan menambahkan solusi grid x by y

Sunting: Saya entah bagaimana melewatkan kendala terakhir tentang keunikan. Script ini menghasilkan semua urutan yang mungkin, bukan hanya 45.

Sunting: Cadangkan hingga 118 tetapi sekarang benar

scleaver
sumber
Ganti ['#','-']dengan'#-'
Winston Ewert
2

J, 35 33 karakter

3 2$"1'-#'{~(2 A.i.6){"1#:20+i.44

Menggunakan pendekatan Ilmari Karonen datang dengan solusi Golfscript mereka. Namun, karena kata kerja J #:(antibase) menyimpan bit (atau, yah, digit dalam case umum) dalam daftar, kita perlu mengindeksnya dari kiri bukan kanan (yaitu indeks 0 adalah bit paling kiri, tertinggi).

Solusinya agak mudah: 20+i.44memberikan daftar angka 20..63, inklusif. #:mengambil antibase-2 dari setiap elemen dalam daftar ini, dan dengan demikian menghasilkan daftar pola bit untuk setiap angka dalam rentang itu. {memilih (pada dasarnya menata ulang) bit ke dalam pola yang tepat, dan kemudian {digunakan kembali untuk menggunakan digit sebagai indeks dalam string '- #' untuk menyiapkan output. Akhirnya, kami mengatur setiap entri ke dalam persegi panjang 2-by-3 dengan $(bentuk).


3 2$"1'-#'{~(2 A.i.6){"1#:20+i.44      N.B. use A. (anagram) to generate the right permutation

3 2$"1'-#'{~0 1 2 4 3 5{"1#:20+i.44

FireFly
sumber
Adakah yang tahu bagaimana sesuatu seperti (0 2 3 ,. 1 4 5) { #: 44dapat diubah agar berfungsi dengan daftar angka dan bukan satu angka? Mungkin akan mencukur beberapa karakter lagi.
FireFly
1

Python - 121 112

kosong tidak termasuk

from itertools import*
print'\n'.join('%s%s\n'*3%b for(b,n)in zip(product(*['_#']*6),range(64))if n&48and n&42)
quasimodo
sumber
Anda dapat memotong produk itu dengan '_#',repeat=6->*['_#']*6
boothby
@ bbyby: terima kasih. Juga, bsudah menjadi tuple, jadi tidak perlu mengubahnya :)
quasimodo