Поверніть двовимірний список на 45 градусів


22

ЗАВДАННЯ

Мета полягає в тому, щоб написати програму, яка обертає будь-який двовимірний список на 45 градусів, перед поверненням списку він повинен бути в змозі зробити це до 7 * 45 (відразу). Список не обов’язково буде квадратним або прямокутним. Ви повинні включити висновок для прикладів у своїй відповіді. Він також повинен працювати у випадках, яких немає в прикладах ... кола, трикутники тощо. Ви не можете використовувати попередньо існуючу функцію, щоб виконати все.

Усі списки матимуть щонайменше одну вісь симетрії (N, S, E, W). Усі підсписи слід вважати вирівняними по центру. Непарні списки змістяться вліво, щоб правильно вирівняти. Дивіться приклад 4 щодо пропусків у середині підпису.

ВХОД

Ваша програма буде використовувати змінну, яка lмістить список, а змінну з іменем, що nвизначає суму, яку список буде обернено (n * 45) ( nзавжди буде менше 7, а може бути 0). Потрібно прийняти, lщо містять підлісти будь-якого типу даних для друку (десятковий, Список, int, String [] .. тощо), але підлісти будуть містити лише один тип даних одночасно.

Вам не потрібно приймати введення консолі або використовувати stdin. Рядки, що вказують тестові значення lта nне включаються до числа символів, але повинні бути включені до поданого коду.

ВИХІД

Ваша програма повинна надрукувати список у правильній орієнтації, NIL можна використовувати для складання списків тампонів, якщо ви хочете, але прокладки не потрібні (ви отримуєте усміхнене обличчя, якщо вони прокладені, хоча). Підсписи не повинні бути відступними або розділеними новими рядками, як у прикладах.

ПРИКЛАДИ

1

IN
l=
[[0 , 1 , 2],
 [3 , 4 , 5],
 [6 , 7 , 8]]
n=1

OUT
[    [0],
   [3 , 1],
 [6 , 4 , 2],
   [7 , 5],
     [8]    ]

2

IN
l=
[[a , b , c , d],
 [e , f , g , h]]
n=2

OUT
[[e , a],
 [f , b],
 [c , g],
 [h , d]]

3

IN
l=
[[A , B , C , D , E , F],
     [G , H , I , J],
         [K , L],
         [0 , 8],
         [M , N],
     [O , P , Q , R],
 [S , T , U , V , W , X]]
n=7

OUT
[          [F],
         [E],
       [D , J],
     [C , I],
   [B , H , L],
 [A , G , K , 8],
           [0 , N , R , X],
             [M , Q , W],
               [P , V],
             [O , U],
               [T],
             [U]          ]

4

IN
l=
[[9 , 8 , 7 , 6],
     [5],
 [4 , 3 , 2 , 1],
     [0]        ]
n=3

OUT
[  [0 , 4],
     [3],
   [2 , 5 , 9],
 [1 ,NIL, 8],
       [7],
     [6],     ]

5

IN
l=
[    [Q],
 [X ,NIL, Y],
     [Z]    ]
n=2

OUT
[    [X],
 [Z ,NIL, Q],
     [Y]     ]

4
Ооо. Це важко. Хоча це виглядає весело!
TheDoctor

1
Два питання: 1) Нам не доведеться вести списки, правда? 2) Ви дійсно хочете, щоб ми повертали список nразів, а не на n45 °? Я прошу, бо я майже впевнений, що я не отримав результат прикладу 3, застосувавши сім обертів на 45 °.
Wrzlprmft

Ні, вам не доведеться колоти. Однак список повинен бути впорядкований у правильній візуальній орієнтації, хоча він не повинен виводитися таким чином ... у висновку не буде нових рядків. Список обертається на n * 45.
Οurous

Відповіді:


8

Пітон - 234 201

# example for defining lists and n
l=[[1,2,3,4],
     [5],
   [6,7,8,9]]
n=1

# counting code
j=1j
m=max(map(len,l))+len(l)
M=range(-m,m)
e=enumerate
d=[[v for x in M for i,u in e(l)for k,v in e(u)if[1,1+j,j,j-1,-1,-j-1,-j,1-j][n]*(k-(len(u)-1)/2+j*i)==x+y*j]for y in M]
print[x for x in d if x]

Безгольова версія

rotation = [1,1+1j,1j,1j-1,-1,-1j-1,-1j,1-1j][n]
m = max(map(len,l))+len(l)
output = []
for y in range(-m,m):
    line = []
    for x in range(-m,m):
        for i,sublist in enumerate(l):
            for k,entry in enumerate(sublist):
                if rotation * ( k-(len(sublist)-1)/2 + i*1j ) == x + y*1j:
                    line += [entry]
    if line != []:
        output += [line]
print output

При цьому використовується те, що множення (на комплексне число) на комплексне число відповідає обертовому і розтягуючому. [1,1+1j,1j,1j-1,-1,-1j-1,-1j,1-1j]- це комплексні числа, що відповідають необхідним кутам, і використовують найменший коефіцієнт масштабування, такий, що для цілого комплексного входу вихід знову є цілим комплексним.


1
Я намагаюся зрозуміти, як це працює, але я втрачаюсь при складних числах. Чи можу я попросити пояснення?
Οurous

1
@Ourous: Нехай x + iy = (x, y), помноживши це на 1 + i = (1,1), ви отримаєте обертання на 45 градусів.
Кайл Канос

Прекрасне рішення. Я намагаюся адаптувати його, щоб він також вставив відповідні прокладки у списки вихідних даних, але мені не пощастило. Це нетривіальне доповнення?
tkocmathla

@tkocmathla: Я цього не тестував, але спробуйте додати else: line += [None]після четвертого з останнього рядка.
Wrzlprmft
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.