Gambar fraktal yang diindeks

14

pengantar

Dalam tantangan ini, matriks 2 × 2 diindeks seperti ini:

0 1
2 3

Kami mendefinisikan keluarga fraktal seperti pola F(L), di mana Lmerupakan panjang- ndaftar indeks ini dan F(L)memiliki ukuran .2n-1 × 2n-1

  • Jika L == [], maka F(L)adalah pola 1 × 1 #.
  • Jika L != [], maka F(L)dibangun sebagai berikut. Membiarkan Pmenjadi pola yang diperoleh dari Ldengan elemen pertama dihapus. Ambil empat kisi ukuran diisi dengan titik , dan ganti kisi diindeks dengan pola . Kemudian, rekatkan kisi-kisi menggunakan satu lapisan hash di antara mereka. Berikut adalah diagram untuk empat kasus:2n-1-1 × 2n-1-1.L[0]P#

    L[0]==0  L[0]==1  L[0]==2  L[0]==3
       #...  ...#     ...#...  ...#...
    [P]#...  ...#[P]  ...#...  ...#...
       #...  ...#     ...#...  ...#...
    #######  #######  #######  #######
    ...#...  ...#...     #...  ...#   
    ...#...  ...#...  [P]#...  ...#[P]
    ...#...  ...#...     #...  ...#   
    

Contoh

Pertimbangkan inputnya L = [2,0]. Kita mulai dengan kisi 1 × 1 #, dan melintasi Ldari kanan. Elemen paling kanan adalah 0, jadi kami mengambil empat salinan dari grid 1 × 1 ., ganti yang pertama dengan #, dan rekatkan bersama-sama dengan hash. Ini menghasilkan kisi 3 × 3

##.
###
.#.

Elemen berikutnya adalah 2, jadi kami mengambil empat salinan dari kisi 3 × 3 ., dan mengganti yang ketiga dengan kisi di atas. Keempat kisi tersebut adalah

...  ...  ##.  ...
...  ...  ###  ...
...  ...  .#.  ...

dan menempelkannya bersama dengan #hasil di kisi 7 × 7

...#...
...#...
...#...
#######
##.#...
####...
.#.#...

Ini adalah hasil akhir kami.

Memasukkan

Input Anda adalah daftar Lindeks 0, 1, 2, 3. Anda dapat menganggapnya sebagai daftar bilangan bulat, atau serangkaian angka. Perhatikan bahwa mungkin kosong, dan mungkin berisi duplikat. Panjangnya Lpaling banyak 5.

Keluaran

Output Anda adalah pola F(L)sebagai string yang dibatasi-baris baru.

Aturan dan penilaian

Anda dapat menulis program atau fungsi lengkap. jumlah byte terendah menang, dan celah standar tidak diizinkan.

Uji kasus

[]
#

[0]
##.
###
.#.

[3]
.#.
###
.##

[2,0]
...#...
...#...
...#...
#######
##.#...
####...
.#.#...

[1,1]
...#.##
...####
...#.#.
#######
...#...
...#...
...#...

[1,2,0]
.......#...#...
.......#...#...
.......#...#...
.......########
.......###.#...
.......#####...
.......#.#.#...
###############
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......

[3,3,1]
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
###############
.......#...#...
.......#...#...
.......#...#...
.......########
.......#...#.##
.......#...####
.......#...#.#.

[0,1,2,3]
.......#...#...#...............
.......#...#...#...............
.......#...#...#...............
.......#########...............
.......#.#.#...#...............
.......#####...#...............
.......#.###...#...............
################...............
.......#.......#...............
.......#.......#...............
.......#.......#...............
.......#.......#...............
.......#.......#...............
.......#.......#...............
.......#.......#...............
###############################
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............
...............#...............

[0,0,1,2,3]
.......#...#...#...............#...............................
.......#...#...#...............#...............................
.......#...#...#...............#...............................
.......#########...............#...............................
.......#.#.#...#...............#...............................
.......#####...#...............#...............................
.......#.###...#...............#...............................
################...............#...............................
.......#.......#...............#...............................
.......#.......#...............#...............................
.......#.......#...............#...............................
.......#.......#...............#...............................
.......#.......#...............#...............................
.......#.......#...............#...............................
.......#.......#...............#...............................
################################...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
...............#...............#...............................
###############################################################
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
...............................#...............................
Zgarb
sumber
Dalam contoh Anda, mengapa Anda mulai dengan kisi 1x1 #? L !=[]dalam contoh itu, karena memiliki 1 atau lebih elemen. Apakah ini berarti bahwa F (L) selalu a# pada awalnya?
R. Kap
2
@ R.Kap Oke, contohnya tidak terlalu jelas. Definisi ini bersifat rekursif, jadi untuk L = [2,0], Anda memenggal kepala dan melihat pola F([0]), lalu memenggal kepala [0]dan melihat pola F([]), yaitu kisi 1x1 #. Kemudian Anda menggunakan indeks yang dipotong 0untuk membangun pola 3x3, dan menggunakan indeks yang dipotong 2untuk yang membangun pola 7x7. Untuk menjawab pertanyaan Anda: ya, Anda selalu mulai dengan kisi 1x1 karena itulah dasar dari rekursi.
Zgarb

Jawaban:

6

CJam, 59 47 43 41 40 byte

Terima kasih kepada Sp3000 untuk menghemat 1 byte.

Sal~W%{_Bff|a4*I@t2/{zSf*z}:F%F}fI3ff+N*

Uji di sini.

Penjelasan

Agak ketinggalan jaman. Akan diperbaiki nanti.

Semua pemesanan dimensi dari daftar 4D membuat saya pusing ...

Kode ini mengimplementasikan spesifikasi dengan sangat harfiah, menggunakan algoritma iteratif dari bagian contoh alih-alih definisi rekursifnya .. Salah satu trik golf utama adalah bahwa saya menggunakan spasi alih-alih #selama perhitungan dan hanya menggantinya dengan #di akhir, yang menyederhanakan kode di satu tempat dan memungkinkan saya untuk menggunakannya Sdaripada '#atau "#"di beberapa tempat.

Sa       e# Push [" "], i.e. a 1x1 grid containing only a space as the
         e# initial fractal.
l~       e# Read and evaluate input.
W%       e# Reverse the list.
{        e# For each list element, assigning the element to variable I...
  _      e#   Duplicate the grid.
  Eff|   e#   Map (OR 14) over each character in the grid, turning spaces into
         e#   periods and leaving periods unchanged.
  a4*    e#   Create an array with four copies of this cleared grid.
  I@t    e#   Replace the Ith element in this list with the previous grid.
  2/     e#   Split this array into a 2x2 grid of subgrids...
         e#   Now it's getting a bit weird... we've got 4 dimensions now, which are:
         e#    - Rows of the 2x2 meta-grid.
         e#    - Cells in each row of the 2x2 meta-grid (i.e. subgrids).
         e#    - Rows of each subgrid.
         e#    - Characters in each row of each subgrid.
  :z     e#   Transpose each outer row, i.e. swap dimensions 2 and 3.
         e#   We've now got in each row of the meta-grid, a list of pairs of
         e#   corresponding rows of the subgrids.
  Sff*   e#   Join those pairs of rows with a single space each. We're now down
         e#   to three dimensions:
         e#    - Rows of the 2x2 meta-grid.
         e#    - Rows of each 1x2 block of the meta-grid.
         e#    - Characters in each row of those blocks.
  :z     e#   Transpose the blocks, i.e. turn the 1x2 blocks into a list of
         e#   columns of their characters.
  z      e#   Transpose the outer grid, i.e. turn it into a list of pairs of
         e#   corresponding columns in the two 1x2 blocks.
  Sf*    e#   Join each pair of columns with a single space. We've now got the
         e#   new grid we're looking for, but it's a list of columns, i.e. transposed.
  z      e#   Fix that by transposing the entire grid once more.
}I
N*       e# Join the rows of the grid with linefeeds.
S'#er    e# Replace all spaces with #.
Martin Ender
sumber
3

MATL , 42 41 byte

'.#'4:He!XIiP"Iq@=wX*1X@WZ(l5MY(]3Lt3$)Q)

Cobalah online!

Penjelasan

Ini berfungsi berulang menggunakan produk Kronecker untuk memperluas array di setiap iterasi. Array dibangun dengan 0dan 1bukannya .dan# , dan pada akhirnya mereka digantikan oleh karakter yang sesuai.

Akan ada iterasi sebanyak ukuran input. Input diproses dari kanan ke kiri. Indeks iterasi dimulai pada1 .

Menggunakan contoh dalam tantangan, dengan input [2,0], array diinisialisasi sebagai

1 2
3 4

Ini sesuai dengan inisial 1( #) diperpanjang oleh satu baris dan satu kolom, yang tujuannya akan jelas nanti. Nilai dalam kolom itu tidak penting, karena akan ditimpa; mereka bisa juga sama:

1 1
1 1

Pada setiap iterasi, array yang ada adalah Kronecker-dikalikan dengan array 2 × 2 nol-satu yang berisi 1posisi yang ditunjukkan oleh entri input saat ini, dan 0pada entri lainnya. Dalam contoh di iterasi i = 1, karena entri input paling kanan adalah 0, array nol-satu adalah

1 0
0 0

dan produk Kronecker dari dua array ini adalah

 1 1 0 0
 1 1 0 0
 0 0 0 0
 0 0 0 0

Selanjutnya, baris dan kolom dengan indeks 2^idiisi dengan yang:

 1 1 0 0
 1 1 1 1
 0 1 0 0
 0 1 0 0

Tiga baris dan kolom pertama merupakan hasil dari iterasi pertama. Seperti sebelumnya, ada baris dan kolom tambahan, yang berguna untuk memperluas array di iterasi berikutnya.

Pada iterasi i = 2, karena nilai input saat ini berisi 2array di atas adalah Kronecker-dikalikan dengan

0 0
1 0

pemberian yang mana

 0 0 0 0 0 0 0 0
 0 0 0 0 0 0 0 0
 0 0 0 0 0 0 0 0
 0 0 0 0 0 0 0 0
 1 1 0 0 0 0 0 0
 1 1 1 1 0 0 0 0
 0 1 0 0 0 0 0 0
 0 1 0 0 0 0 0 0

Mengisi 2^ibaris dan kolom -th dengan yang memberi

 0 0 0 1 0 0 0 0
 0 0 0 1 0 0 0 0
 0 0 0 1 0 0 0 0
 1 1 1 1 1 1 1 1
 1 1 0 1 0 0 0 0
 1 1 1 1 0 0 0 0
 0 1 0 1 0 0 0 0
 0 1 0 1 0 0 0 0

Karena ini adalah iterasi terakhir, baris dan kolom tambahan dihapus:

 0 0 0 1 0 0 0
 0 0 0 1 0 0 0
 0 0 0 1 0 0 0
 1 1 1 1 1 1 1
 1 1 0 1 0 0 0
 1 1 1 1 0 0 0
 0 1 0 1 0 0 0

dan penggantian karakter dilakukan untuk menghasilkan hasil akhir:

...#...
...#...
...#...
#######
##.#...
####...
.#.#...

Penjelasan terperinci dari kode berikut:

'.#'      % Push this string. Will be indexed into
4:He!     % Push 2×2 array [1 2; 3 4]
XI        % Copy it into clipboard I
iP        % Input array and reverse it
"         % For each entry of the reversed input
  I       %   Push [1 2; 3 4] from clipboard I
  q       %   Subtract 1 to yield [0 1; 2 3]
  @=      %   Compare with current entry of the input. Gives 2×2 array
          %   with an entry equal to `1` and the rest `0`
  wX*     %   Swap. Kronecker product
  1       %   Push 1
  X@      %   Push iteration index, i
  W       %   Compute 2^i
  Z(      %   Write 1 into column 2^i
  l       %   Push 1
  5M      %   Push 2^i again
  Y(      %   Write 1 into row 2^i
]         % End for each
3Lt       % Push [1, -1j] (corresponding to index 1:end-1) twice
3$)       % Apply index. Removes last row and column
Q         % Add 1. Gives an array of values 1 and 2
)         % Index into initial string
Luis Mendo
sumber
2

Haskell, 123 122 byte

unlines.foldr(#)["#"]
n#p=zipWith(++)(r++h:t)$('#':)<$>u++h:s where b='.'<$p<$p;h='#'<$p;(r:s:t:u:_)=drop n$cycle[p,b,b,b]

Contoh penggunaan:

*Main> putStr $ (unlines.foldr(#)["#"]) [2,3,1]
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
.......#.......
###############
...#...#.......
...#...#.......
...#...#.......
########.......
...#.###.......
...#####.......
...#.#.#.......

Bagaimana itu bekerja:

                ["#"]      -- starting with "#" 
        foldr(#)           -- fold the function # from the right into the input
unlines                    -- and join the result with newlines

n#p=                       -- helper function #
                           -- n: next index, p: fractal so far
    zipWith(++)            -- join the left and right part elementwise
       (r++h:t)            -- left part
       ('#':) <$> u++h:s   -- right part (prepend '#' to each line for vertical
                           -- separator

                           -- helper
b='.'<$p<$p                -- b is a blank square of the same size as p
h='#'<$p                   -- h is a line of '#' of the same length as p
(r:s:t:u:_)=               -- drop the first n elements of the infinite
    drop n$cycle[p,b,b,b]  --   list [p,b,b,b,p,b,b,b,p,b,b,b,...] and
                           --   assign the next 4 element to r,s,t,u.
                           --   As r,s,t,u are always inserted at the
                           --   same position in the fractal, we get the
                           --   variants by assigning different values.
nimi
sumber
1

JavaScript (ES6), 171 152 byte

([d,...a],h=`#`,r=`replace`)=>d<4?(s=f(a)[r](/.+/g,s=>(t=s[r](/./g,`.`),d&1?t+h+s:s+h+t)),t=s[r](/.+/g,w=t+h+t),w=`
${w[r](/./g,h)}
`,d&2?t+w+s:s+w+t):h

Mengambil hasil dari panggilan rekursif, lalu mengganti setiap baris dengan dirinya sendiri ditambah hash plus serangkaian titik dengan panjang yang sama, dalam urutan terbalik jika perlu, kemudian dari hasil parsial itu menciptakan serangkaian titik kecuali untuk baris baru dan kolom tengah hash, dan juga serangkaian hash dengan baris baru yang mengelilinginya, kemudian menggabungkan ketiga string tersebut bersama-sama dalam urutan yang sesuai.

Neil
sumber
1

Ruby, 143 134 byte

Fungsi anonim.

1 byte disimpan oleh penataan ulang baris pertama. 6 byte disimpan dengan mengubah cara z bertambah dari rumus ke tabel. 2 byte disimpan dengan menghilangkan varable w.

->a{r=-1+u=2<<a.size
s=(?.*r+$/)*r
a<<0
z=r*u/2-1
a.each{|i|r/=2
(-r..r).each{|j|s[z+j]=s[z+j*u]=?#}
z+=-r/2*[u+1,u-1,1-u,-u-1][i]}
s}

Tidak digabungkan dalam program uji

f=->a{
  r=w=(u=2<<a.size)-1        #w=length of line excluding newline, u=length of line including newline.
  s=(?.*w+$/)*w              #initialize string s with w rows of w dots terminated by newlines.
  z=w*u/2-1                  #z is the centre of the fractal
  a<<0                       #add a dummy value to the end of a
  a.each{|i|                 #for each element in a
    r/=2                     #r is the radius of the current iteration: ....15,7,3,1
    (-r..r).each{|j|         #for j=-r to r
      s[z+j]=s[z+j*u]=?#     #overwrite . with #, forming horizontal and vertical lines
    }
    z+=-r/2*(u+1)+           #move z to centre of upper left quarter (where it should be if i=0)
      i%2*(q=r+1)+           #move across if i=1,3
      i/2%2*q*u              #and down if i=2,3  
  }
s}                           #return string

puts $/,f[[]]

puts $/,f[[0]]

puts $/,f[[3]]

puts $/,f[[2,0]]

puts $/,f[[1,1]]

puts $/,f[[1,2,0]]

puts $/,f[[3,3,1]]

puts $/,f[[0,1,2,3]]

puts $/,f[[0,0,1,2,3]]
Level River St
sumber
0

Ruby, 150 byte

Fungsi anonim. Menggunakan panggilan rekursif untuk membuat daftar string, satu string per baris, kemudian bergabung bersama-sama di akhir.

->i{f=->l{s=2**l.size-1;g=[[?.*s]*s]*4;m=->x,y{x.zip(y).map{|a,b|a+?#+b}}
s<1?[?#]:(g[l.shift]=f[l];m[*g[0,2]]+[?#*(2*s+1)]+m[*g[2,2]])}
f[i].join"
"}
Nilai Tinta
sumber
0

Python 3.5, 1151 byte:

Tidak banyak kode golf, tapi oh well. Akan mencoba memangkasnya lebih dari waktu di mana saya bisa.

def x(s):
 y=[''];l=['#'];k=[' ']
 for z in s[::-1]:y.append(z)
 y=y[::-1]
 for h in range(len(y)):
  if y[-1]!='':u=(int(y.pop())&3)
  else:u=y.pop()
  if len(l)<2:k.append(u);p=((2**(len(k)-1))-1);l.append((('.'*p+'#'+'.'*p+'\n')*p)+'#'*((p*2)+1)+'\n'+(('.'*p+'#'+'.'*p+'\n')*p))
  else:
   if len(l)>2:del l[0]
   p=((2**(len(k)-1))-1);a=[[_+i for i in range(p)]for _ in range(len(l[1]))if _%((p*2)+2)==0 and _!=(((p*2)+2)*(p))];b=[[_+i for i in range(p)]for _ in range(len(l[1]))if _%(int(((p*2)+2)/2))==0 and _!=(int(((p*2)+2)/2)*((p)*2))and _ not in[g for i in a for g in i]];W=[g for i in a[:len(a)-(int(len(a)/2)):1]for g in i];B=[g for i in b[:len(b)-(int(len(b)/2)):1]for g in i];C=[g for i in a[len(a)-(int(len(a)/2)):len(a):1]for g in i];T=[g for i in b[len(b)-(int(len(b)/2)):len(b):1]for g in i];f=list(l[1])
   for i in list(''.join(l[0].split())):
    if u==0:f[W[0]]=i;del W[0]
    elif u==1:f[B[0]]=i;del B[0]
    elif u==2:f[C[0]]=i;del C[0]
    elif u==3:f[T[0]]=i;del T[0]
   del l[0];k.append(u);p=((2**(len(k)-1))-1);l.append(''.join(f));l.append((('.'*p+'#'+'.'*p+'\n')*p)+'#'*((p*2)+1)+'\n'+(('.'*p+'#'+'.'*p+'\n')*p))
 print(l[-2])

Cara yang cukup naif untuk melakukan ini, tetapi, bagaimanapun, saat ini berfungsi dengan baik dan, seperti yang Anda lihat, tidak menggunakan modul / perpustakaan eksternal. Selain itu, dapat mengambil cara yang lebih dari 5 item dalam daftar yang disediakan stanpa kehilangan akurasi apapun (yaitu, jika perangkat keras Anda bisa mengatasinya). Itu memenuhi semua persyaratan, dan saya tidak bisa lebih bahagia dengan apa yang saya dapatkan. :)

Sekarang juga tidak hanya dapat menerima angka dalam kisaran 0=>3sebagai nilai apa pun , tetapi nomor , periode apa pun , berkat &operator bitwise! Anda dapat membaca lebih lanjut tentang mereka di sini . Sekarang, misalnya, [4,4,1,2,3]karena daftar input sama dengan [0,0,1,2,3].

Catatan: Input harus disediakan sebagai daftar

Tidak digabungkan dengan penjelasan:

def x(s):
 # Create 3 lists:
 # `y` is for the values of `s` (the list provided) and an empty element for the 
 # first pattern
 # `l` is reserved for the pattersn created through each item in list `y`
 # `k` is created for the value of `p` which is the main value through which the 
 # pattern is created.
 y=[''];l=['#'];k=[' ']
 # Reverse s, and then add each element from `s` to `y` 
 # (in addition to the empty element) 
 for z in s[::-1]:
     y.append(z)
 # `y` should now equal the list created, but reversed
 # If not reversed, then, if, for instance, the input is `0,1,2` and list `y` 
 # therefore contains `'',2,1,0`, the empty element will be called at the end, 
 # which is NOT what we want.
 y=y[::-1]
 # The main loop; will be iterated through the length of `y` number of times
 for h in range(len(y)):
  # Here is where each element from the end of `y` is recieved as `u` for 
  # use in the pattern in each iteration.
  # As you can also see, a bitwise operator (`&`) is used here so that 
  # ALL numbers can be accepted. Not just those in the range `0-4`.     
  # However, that will happen only if the value of y[-1] (the last elment in y) is 
  # NOT ''.
  if y[-1]!='':
      u=(int(y.pop())&3)
  else:
      u=y.pop()
  # If the length of list `l` is less than 2 
  # (which means it only contains `#`), then do the following:
  if len(l)<2:
      # Append `u` to `k`
      k.append(u)
      # Use the length of `k` as `n` in the operation `(2^(n-1)-1)` to get the 
      # length of the dot filled part of the new pattern.
      p=((2**(len(k)-1))-1)
      # Add that pattern to the list (currently empty, 
      # i.e. containing no other pattern in any other quadrant)
      l.append((('.'*p+'#'+'.'*p+'\n')*p)+'#'*((p*2)+1)+'\n'+(('.'*p+'#'+'.'*p+'\n')*p))
  # Now, if the length of l is >=2, do the following:
  else:
   # If the length of l is >2, then delete the first element in list `l` 
   # (this will happen only once, when the `#` is still the first element)
   if len(l)>2:
       del l[0]
   # Again, use the length of `k` as `n` in the operation `(2^(n-1)-1)`
   # to get the length of the dot filled part of the pattern.
   p=((2**(len(k)-1))-1)
   # Create a list with all the index values of all the dot elements on the left hand 
   # side of the grid l[-1], and the index value + i where i is every integer in 
   # the range `0-p` (this way, it will create lists within a list, each 
   # which contain `p` number of integers, which are all indexes of all the dots on 
   # the very left side of the grid) 
   a=[[_+i for i in range(p)]for _ in range(len(l[1]))if _%((p
      *2)+2)==0 and _!=(((p*2)+2)*(p))]
   # Create another list with all the index values of the dots using the same 
   # strategy as above, but this time, those in the right half of the grid. 
   b=[[_+i for i in range(p)]for _ in range(len(l[1]))if _%(int(((p*2)+2)/2))==0 
      and _!=(int(((p*2)+2)/2)*((p)*2))and _ not in[g for i in a for g in i]]
   # Create 4 lists, each containing index values specific to each of the 
   # 4 quadrants of the grid.
   # W is the list, based on A, containing all the indexes for the 1st quadrant of 
   # the grid in l[-1] containing dots (index 0 in the grid)
   W=[g for i in a[:len(a)-(int(len(a)/2)):1]for g in i]
   # B is the list, this time based on b, containing all indexes for the 2nd 
   # dot-filled quadrant of the grid l[-1] (index 1 in the grid)
   B=[g for i in b[:len(b)-(int(len(b)/2)):1]for g in i]
   # C is the list, also, like W, based on a, containg all the index values for 
   # the 3rd dot-filled quadrant of the grid in l[-1] (index 2 in the grid)
   C=[g for i in a[len(a)-(int(len(a)/2)):len(a):1]for g in i]
   # T is the final list, which, also like B, is based on b, and contains all the 
   # index values for the final (4th) dot-filled quadrant of the grid in l[-1] 
   T=[g for i in b[len(b)-(int(len(b)/2)):len(b):1]for g in i];f=list(l[1])
   # Finally, in this `for` loop, utilize all the above lists to create the new 
   # pattern, using the last two elements in list `l`, where each character of grid 
   # l[-2] (the second to last element) is added to the correct index of grid l[-1] 
   # based on the value of `u`
   for i in list(''.join(l[0].split())):
    if u==0:
        f[W[0]]=i
        del W[0]
    elif u==1:
        f[B[0]]=i
        del B[0]
    elif u==2:
        f[C[0]]=i
        del C[0]
    elif u==3:
        f[T[0]]=i
        del T[0]
   # Delete the very first element of `l`, as it is now not needed anymore
   del l[0]
   # Append `u` to list`k` at the end of the loop this time
   k.append(u)
   # Update the value of `p` with the new value of length(k)
   p=((2**(len(k)-1))-1)
   # Append the new patter created from the for-loop above to list `l`
   l.append(''.join(f))
   # Append a new, empty pattern to list `l` for use in the next iteration
   l.append((('.'*p+'#'+'.'*p+'\n')*p)+'#'*((p*2)+1)+'\n'+(('.'*p+'#'+'.'*p+'\n')*p))
 # When the above main loop is all finished, print out the second-to-last elment in 
 # list `l` as the very last element is the new, empty grid created just in case 
 # there is another iteration
 print(l[-2])

Penjelasan yang lebih luas & jauh lebih menarik secara visual:

Untuk penjelasan yang lebih luas dan jauh lebih menarik secara visual, pertimbangkan untuk kedua kalinya melalui "main" -Loop dalam kode di atas, di mana daftar inputnya [0,2]. Dalam hal ini, elemen dalam daftar "utama" ladalah:

.#.
###
##.

dan

...#...
...#...
...#...
#######
...#...
...#...
...#...

dan daftar yhanya akan berisi 0. Mengambil keuntungan dari cara Python untuk mengindeks elemen terakhir grid l[-1], kita dapat memberi label elemen paling kiri dari grid seperti:

 0 ...#...\n 7        
 8 ...#...\n 15
16 ...#...\n 23
   #######\n <- Ignore this as it is nothing but `#`s and a new line
32 ...#...\n 39
40 ...#...\n 47
48 ...#...\n 55

Pola apa yang Anda lihat? Setiap indeks di paling kiri dari grid adalah kelipatan dari 8, dan karena, dengan menggunakan persamaan 2^(n-1)-1menghasilkan panjang setiap segmen dari titik-titik dalam grid, kita dapat melakukan ((2^(n-1)-1)*2)+2untuk menemukan panjang tepi atas grid secara keseluruhan (+2 untuk memasukkan tengah #dan \nakhir). Kita dapat menggunakan persamaan itu, yang akan kita panggil iuntuk menemukan nilai indeks setiap elemen di sisi kiri kisi ukuran apa pun dengan membuat daftar, dan menambahkan ke daftar setiap bilangan bulat, yang akan kita panggil _, dalam rentang 0=>length of grid l[-1], sedemikian sehingga item tersebut adalah kelipatan i, DAN juga sedemikian sehingga _TIDAK sama i*(2^(n-1)-1), sehingga kita dapat mengecualikan segmen tengah#s memisahkan bagian atas dari bagian bawah. Tapi kami ingin SEMUA elemen titik dari kiri, dan bukan hanya elemen di sisi paling kiri. Nah, ada perbaikan untuk itu, dan itu hanya akan menambahkan ke daftar daftar yang berisi di i+hmana h adalah setiap bilangan bulat dalam rentang 0=>2^(n-1)setiap kali nilai dari rentang 0=>length of grid l[-1]ditambahkan ke daftar, sehingga setiap kali, akan ada sebanyak jumlah nilai yang ditambahkan ke daftar sebagai panjang satu kuadran titik. Dan itu adalah daftar a.

Tapi sekarang, bagaimana dengan titik-titik di sebelah kanan? Baiklah, mari kita lihat pengindeksannya dengan cara yang berbeda:

   0 ...# 4  ...\n 7        
   8 ...# 12 ...\n 15
  16 ...# 20 ...\n 23
     #######\n <- Ignore this as it is nothing but `#`s and a new line
  32 ...# 36 ...\n 39
  40 ...# 44 ...\n 47
  48 ...# 52 ...\n 55

          ^
          | 

          These are the values we are looking at now

Seperti yang Anda lihat, nilai sekarang di tengah adalah yang kita butuhkan, karena mereka adalah awal dari indeks setiap segmen titik di sisi kanan grid. Sekarang, apa polanya di sini? Nah, jika itu belum cukup jelas, sekarang nilai tengah semua kelipatan i/2! Dengan informasi itu, kita sekarang dapat membuat daftar lain, bdimana kelipatan i/2ditambahkan dari jangkauan 0=>length of grid l[-1]sehingga setiap bilangan bulat dari rentang itu, yang akan kita panggil lagi _, TIDAK sama dengan (i/2)*(p*2)untuk mengecualikan garis #s yang memisahkan bagian atas dan bagian bawah, DAN sedemikian rupa sehingga _ TIDAK sudah ada dalam daftar a, karena kita tidak benar-benar membutuhkan 8,16,32, dll. dalam daftarb . Dan sekarang, sekali lagi, kami tidak hanya menginginkan indeks spesifik itu. Kami ingin SEMUA karakter titik di sisi kanan kotak. Yah, sama seperti yang kami lakukan dalam daftar a, di sini kami juga dapat menambahkan ke daftar bdaftar_+h mana hsetiap bilangan bulat dalam kisaran 0=>2^(n-1).

Sekarang, kami memiliki daftar adan bdikemas dan siap untuk pergi. Bagaimana kita menyatukan ini sekarang? Di sinilah daftar W, T, G, dan Cmasuk. Mereka akan memegang indeks untuk masing-masing kuadran tertentu dari titik-titik dalam grid l[-1]. Sebagai contoh, mari kita daftar cadangan Wsebagai daftar untuk semua indeks yang sama dengan kuadran 1 (indeks 0) dari kisi. Dalam daftar ini, kami kemudian akan menambahkan 2^(n-1)daftar pertama dari daftar a, karena daftar aberisi semua indeks untuk titik-titik di bagian kiri kotak, dan kemudian membaginya semua sehingga Wsekarang berisi (2^(n-1))*(2^(n-1))elemen. Kami akan melakukan hal yang sama untuk daftar T, tetapi dengan perbedaan yang Takan mengandung elemen dari daftar b, sejak ituTdicadangkan untuk kuadran 2 (indeks 1). Daftar Gakan sama dengan daftar W, kecuali itu akan berisi sisa elemen dari daftar a, dan daftar Csama dengan daftar T, kecuali sekarang berisi sisa elemen dari daftar b. Dan itu dia! Kami sekarang memiliki nilai indeks untuk setiap kuadran yang berisi titik-titik dalam kisi, semua dibagi menjadi empat daftar yang sesuai dengan setiap kuadran. Kita sekarang dapat menggunakan 4 daftar ini (W, T, G, C) untuk memberi tahu program karakter mana yang harus diganti dalam kotak l[-1]dengan masing-masing karakter dari kotak l[0], yang merupakan elemen paling pertama dari daftar l. Karena nilainya ada di 0sini, itu akan mengganti semua titik di kuadran pertama (indeks 0) dengan l[0]daftar pemanfaatan kisiW.

Karena itu, kami akhirnya memiliki yang berikut:

.#.#...
####...
##.#...
#######
...#...
...#...
...#...

Wah! Proses yang panjang, bukan? Namun, itu bekerja dengan sempurna, dan, sekali lagi, saya tidak bisa lebih bahagia. :)

R. Kap
sumber