2015-10-06 24 views
6

Sto cercando di ruotare un elenco di lista di 90 gradi. Ad esempio, modificare questo:indice di lista fuori intervallo, ogni volta che cambio la dimensione dell'elenco

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

a

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

visivamente:

[[1,2,3],   [[7,4,1], 
[4,5,6], -->  [8,5,2], 
[7,8,9]]   [9,6,3]] 

ogni volta che cambia la dimensione elenco da più elementi o meno si dice sempre l'indice è fuori gamma? Cosa sta succedendo?

def rotate(list1): 
    bigList = [] #create a list that we will append on to 
    for i in (range(len(list1)+1)): #loop through the list looking at the indexes 
     newList = [] 
     for j in reversed(range(len(list1))): #reverse that list 
      newList.append(list1[j][i]) 
     bigList.append((newList)) #append the elements to the bigList reversed 
    return bigList 
+0

Il vostro rientro postato qui è corretto? –

+0

@AnandSKumar Non penso che lo sia, e anche la sua lista non è giusta. – Leb

+0

@AnandSKumar Dovrebbe essere corretto ora, mi dispiace per il fatto che mi sto ancora abituando ai blocchi di codice mentre lo digito in –

risposta

4

Quello che state facendo può essere facilmente fatto in una singola linea utilizzando reversed e zip. Problema effettivo nel codice fornito di seguito in questa risposta.

Esempio -

list(zip(*reversed(yourlist))) 

Non è necessario il list(...) per Python 2.x, come zip() restituisce una lista in Python 2.x.

Demo -

>>> list(zip(*reversed([[1,2,3], [4,5,6], [7,8,9]]))) 
[(7, 4, 1), (8, 5, 2), (9, 6, 3)] 
>>> list(zip(*reversed([[1,2,3,4], [5,6,7,8], [9,10,11,12]]))) 
[(9, 5, 1), (10, 6, 2), (11, 7, 3), (12, 8, 4)] 

Se si desidera una lista di liste, invece di lista di tuple, è possibile utilizzare di lista (o map(list, zip(*reversed(....)))). Esempio -

[list(x) for x in zip(*reversed(yourlist))] 

Demo -

>>> [list(x) for x in zip(*reversed([[1,2,3], [4,5,6], [7,8,9]]))] 
[[7, 4, 1], [8, 5, 2], [9, 6, 3]] 
>>> [list(x) for x in zip(*reversed([[1,2,3,4], [5,6,7,8], [9,10,11,12]]))] 
[[9, 5, 1], [10, 6, 2], [11, 7, 3], [12, 8, 4]] 

* è la sintassi per la decompressione, quindi la lista restituita da reversed() viene decompresso in zip() e passato come argomenti separati ad esso.

Quindi la funzione zip() combina gli elementi di ciascun argomento nel suo indice corrispondente (come tutti i primi argomenti insieme, tutti i secondi argomenti insieme, ecc.), Quindi otteniamo il risultato di cui abbiamo bisogno.


Il problema effettivo per il codice originale si è verificato a causa della seguente riga -

for i in (range(len(list1)+1)): 

Stai loop fino len(list1) + 1, da qui alla fine si tenta di accedere a elementi come list1[0][len(list1)], ma che non esiste in il tuo caso.

Supponendo che il sottolista di list1 abbia la stessa quantità di elementi, ciò di cui si ha realmente bisogno sarà len(list1[0]).Esempio -

def rotate(list1): 
    bigList = [] #create a list that we will append on to 
    for i in (range(len(list1[0]))): #loop through the list looking at the indexes 
     newList = [] 
     for j in reversed(range(len(list1))): #reverse that list 
      newList.append(list1[j][i]) 
     bigList.append((newList)) #append the elements to the bigList reversed 
    return bigList 

Demo -

>>> def rotate(list1): 
...  bigList = [] #create a list that we will append on to 
...  for i in (range(len(list1[0]))): #loop through the list looking at the indexes 
...   newList = [] 
...   for j in reversed(range(len(list1))): #reverse that list 
...    newList.append(list1[j][i]) 
...   bigList.append((newList)) #append the elements to the bigList reversed 
...  return bigList 
... 
>>> rotate([[1,2,3], [4,5,6], [7,8,9]]) 
[[7, 4, 1], [8, 5, 2], [9, 6, 3]] 
>>> rotate([[1,2,3,4], [5,6,7,8], [9,10,11,12]]) 
[[9, 5, 1], [10, 6, 2], [11, 7, 3], [12, 8, 4]] 

+1

Potresti spiegare cosa sta succedendo nella lista 'line (zip (* invertita (...)))' e cosa significa '*' qui? –

+1

'*' è la sintassi per decomprimere, quindi l'elenco restituito da 'reverseed()' è decompresso in 'zip()' e passato come argomenti separati. Quindi la funzione 'zip()' combina gli elementi di ciascuno dei suoi argomenti nel suo indice corrispondente (come tutti i primi argomenti insieme, tutti i secondi argomenti insieme, ecc.), Quindi otteniamo il risultato di cui abbiamo bisogno. Aggiornato questo nella risposta. –

1

Change

for i in (range(len(list1)+1)) 

a

for i in (range(len(list1))) 

e dovrebbe funzionare

+0

non funziona se ho più elementi nell'elenco delle liste, per esempio si blocca su [[1,2,3,4], [5,6,7,8], [9,10,11, 12]] –

0

Se si modifica la linea for i a:

for i in (range(len(list1))): 

allora si dà il risultato atteso.

Nota che il codice funziona solo per le liste n-by-n e non per le liste n-by-m

Tipico esempio di off by one error ;-)

Problemi correlati