Manipulando listas com #Python. (#dev)

Neste post, mostro um pouco das funcionalidades para acessar elementos, mesclar listas, mostrar listas no sentido inverso, iterar sobre a lista de 2 em 2 elementos, etc.

Primeiro, para todos os exemplos, vou usar as seguintes listas:

foo = ["00 bacon", "01 foo", "02 bar", "03 lettuce", "04 pancakes", "05 waffles"]
bar = [0, 1, 1, 2, 3, 5]

 

Mesclando listas

É possível mesclar listas da mesma forma que você passa *args para funções…

foobar = [*foo, *bar]


['00 bacon',
 '01 foo',
 '02 bar',
 '03 lettuce',
 '04 pancakes',
 '05 waffles',
 0,
 1,
 1,
 2,
 3,
 5]

 

 

Acessando o elemento n da lista

Este é o comportamento normal de qualquer lista/array que conhecemos. Não quis deixar o básico de fora…

foo[0]

'00 bacon'

 

 

Acessando o último elemento da lista

Sem funcionalidades como linq, geralmente você tem que pegar o tamanho da lista e subtrair 1 para saber o índice do último item da lista. No Python é só usar -1 como índice.

foo[-1]

'05 waffles'

 

 

Acessando o penúltimo elemento da lista

Esta lógica não é apenas para o último item. Você pode utilizar números negativos para percorrer a lista ao contrário (não é a melhor opção para isso, mas é uma das possibilidades).

foo[-2]

'04 pancakes'

 

 

Pulando n itens da lista

É possível utilizar as listas “pulando” ou ignorando os n primeiros itens dela.

foo[1:]

['01 foo', '02 bar', '03 lettuce', '04 pancakes', '05 waffles']

 

 

Pegando n itens da lista

De forma similar, você pode apenas pegar um número limitado de itens da lista, ao invés de pegar a lista toda de uma vez.

foo[:3]

['00 bacon', '01 foo', '02 bar']

 

 

Pegando uma “fatia” da lista

É possível combinar a lógica de “pular n itens” e “pegar n itens”, mas essa abordagem tem um detalhe importante.

foo[2:4] 

['02 bar', '03 lettuce']

O detalhe aqui é o seguinte, primeiro você vai pegar os 4 primeiros itens e depois vai ignorar os 2 primeiros. É um pouco contraintuitivo de ler, já que o “comando” para pular os dois primeiros itens vem primeiro, mas a ideia é essa: Primeiro você separa os itens que vai utilizar, depois vc “aplica” o filtro de ignorar itens.

Neste caso, para o comando de “pegar n itens” você não precisa se preocupar com o tamanho da lista. O Python vai te devolver o número de itens que você pediu até chegar ao final da lista. Se ele não possuir a quantidade de elementos que você pediu, paciência. Seu resultado será uma lista menor. Veja este segundo exemplo:

foo[2:940000]

['02 bar', '03 lettuce', '04 pancakes', '05 waffles']

Veja que peguei os 940.000 itens e ignorei os 2 primeiros. Minha lista s;o tinha 6 elementos, então o meu resultado contempla apenas os 4 últimos elementos.

 

 

Iterando pela lista, 2 elementos por vez

Geralmente, quando fazemos um for em uma lista, ele passa por todos os elementos, mas você pode querer que ele passe por 1 e pule 1.

foo[::2] 


['00 bacon', '02 bar', '04 pancakes']

Sim, tem outro : no processo. Ele sempre existiu em todos os outros exemplos, mas quando ele é omitido, o padrão é 1.

 

 

Invertendo a lista

Você pode usar a abordagem anterior, combinada com os outros exemplos deste post para inverter a ordem da lista.

foo[::-1]

['05 waffles', '04 pancakes', '03 lettuce', '02 bar', '01 foo', '00 bacon']

 

Que tal inverter a lista, pegando um elemento e ignorando o outro?

foo[::-2]

['05 waffles', '03 lettuce', '01 foo']

 

Outra forma de inverter uma lista é utilizando a função reversed

reversed(foo)


<list_reverseiterator at 0x5cef000>

Porém ela retorna um generator e não a lista invertida. Utilizando este método, para pegar a lista invertida, você precisaria converte-la:

list(reversed(foo)) 

['05 waffles', '04 pancakes', '03 lettuce', '02 bar', '01 foo', '00 bacon']

 

Então, quando usar foo[::-1] e quando usar reversed(foo)? Bom, depende do que você precisar, do tamanho das listas, dos requerimentos de desempenho, etc.

 

 

Iterando por duas listas ao mesmo tempo

É possível fazer um for e passar por duas listas ao mesmo tempo.

for f, b in zip(foo, bar):
    print(f"This is an element of foo: {f}")
    print(f"This is an element of bar: {b}")


This is an element of foo: 00 bacon
This is an element of bar: 0
This is an element of foo: 01 foo
This is an element of bar: 1
This is an element of foo: 02 bar
This is an element of bar: 1
This is an element of foo: 03 lettuce
This is an element of bar: 2
This is an element of foo: 04 pancakes
This is an element of bar: 3
This is an element of foo: 05 waffles
This is an element of bar: 5

 

Se precisar, consegue também incluir um índice nesta operação:

for i, (f, b) in enumerate(zip(foo, bar)): 
    print(f"[{i}] This is an element of foo: {f}")
    print(f"[{i}] This is an element of bar: {b}")


[0] This is an element of foo: 00 bacon
[0] This is an element of bar: 0
[1] This is an element of foo: 01 foo
[1] This is an element of bar: 1
[2] This is an element of foo: 02 bar
[2] This is an element of bar: 1
[3] This is an element of foo: 03 lettuce
[3] This is an element of bar: 2
[4] This is an element of foo: 04 pancakes
[4] This is an element of bar: 3
[5] This is an element of foo: 05 waffles
[5] This is an element of bar: 5

 

Existe um detalhe importante! Se as listas forem de tamanhos diferentes, a iteração será feita pegando o número de elementos das menor lista.

bar2 = [42, *bar]
for i, (f, b) in enumerate(zip(foo, bar2)):  # Attention! if the lists have different sizes, will iterate the number of elements of the first list.
    print(f"[{i}] This is an element of foo: {f}")
    print(f"[{i}] This is an element of bar: {b}")

print("Note that 5 (last element of bar2) was not included in the for")


[0] This is an element of foo: 00 bacon
[0] This is an element of bar: 42
[1] This is an element of foo: 01 foo
[1] This is an element of bar: 0
[2] This is an element of foo: 02 bar
[2] This is an element of bar: 1
[3] This is an element of foo: 03 lettuce
[3] This is an element of bar: 1
[4] This is an element of foo: 04 pancakes
[4] This is an element of bar: 2
[5] This is an element of foo: 05 waffles
[5] This is an element of bar: 3
Note that 5 (last element of bar2) was not included in the for

No exemplo acima, a lista foo tem um elemento a menos que a lista bar2 e isso fez com que o último elemento da lista bar2 fosse ignorado.

 

 

Realizando operações em cada item da lista

Uma forma rápida e limpa de multiplicarmos todos os elementos da lista bar por 2.

x = [n*2 for n in bar] 
print(bar)
print(x)


[0, 1, 1, 2, 3, 5]
[0, 2, 2, 4, 6, 10]

 

 

Utilizando all e any

All e any são funções que não manipulam listas, mas são muito úteis e resolvi incluir aqui

x = [n % 2 == 0 for n in bar]
print(bar)
print(x)
print(f"All elements of bar are even numbers? - {all(x)}")
print(f"Any elements of bar is an even number? - {any(x)}")

Acimn eu criar a lista x, que contem apenas true ou false, indicando se o elemento correspondente na lista bar é ou não par.

Quando chamo a função all, ela retorna true se todos os elementos de x forem true. De forma similar, any vai retornar true se pelo menos 1 item da lista x for true.

 

 

É isso. Espero ter ajudado!

The following two tabs change content below.
Arquiteto de Software e Desenvolvedor Backend (quase Fullstack), geralmente trabalho com C#, PowerShell, Python, Golang, bash e Unity (esse é mais por hobby). Estou sempre buscando algo novo para aprender, adicionando novas ferramentas ao meu cinto de utilidades.
Posted in Dev, Python and tagged , , , .