una - sommare elementi lista python




Come trovare l'ultima occorrenza di un oggetto in un elenco Python (8)

È possibile utilizzare il fatto che le chiavi del dizionario sono univoche e quando si costruisce una con le tuple verrà utilizzato solo l'ultimo attributo di un valore per una determinata chiave. Come indicato in altre risposte, questo va bene per gli elenchi di piccole dimensioni, ma crea un dizionario per tutti i valori univoci e potrebbe non essere efficace per elenchi di grandi dimensioni.

dict(map(reversed, enumerate(li)))["a"]

6

Dì che ho questa lista:

li = ["a", "b", "a", "c", "x", "d", "a", "6"]

Per quanto mi ha mostrato aiuto, non esiste una funzione incorporata che restituisca l'ultima occorrenza di una stringa (come il rovescio index ). Quindi, in pratica, come posso trovare l'ultima occorrenza di "a" nella lista data?


Ecco un piccolo formulario per ottenere l'ultimo indice, usando enumerate e una lista di comprensione:

li = ["a", "b", "a", "c", "x", "d", "a", "6"]
[l[0] for l in enumerate(li) if l[1] == "a"][-1]

Molte altre soluzioni richiedono un'iterazione sull'intero elenco. Questo no.

def find_last(lst, elm):
  gen = (len(lst) - 1 - i for i, v in enumerate(reversed(lst)) if v == elm)
  return next(gen, None)

Modifica: Con il senno di poi sembra una magia inutile. Farei invece qualcosa del genere:

def find_last(lst, sought_elt):
    for r_idx, elt in enumerate(reversed(lst)):
        if elt == sought_elt:
            return len(lst) - 1 - r_idx

Se in realtà stai usando solo singole lettere come mostrato nell'esempio, str.rindex funzionerebbe facilmente. Ciò solleva ValueError se non esiste un tale elemento, la stessa classe di errore che list.index avrebbe list.index . demo:

>>> li = ["a", "b", "a", "c", "x", "d", "a", "6"]
>>> ''.join(li).rindex('a')
6

Nel caso più generale, è possibile utilizzare list.index nell'elenco invertito:

>>> len(li) - 1 - li[::-1].index('a')
6

L'affettatura qui crea una copia dell'intera lista. Va bene per le liste brevi, ma nel caso in cui li sia molto grande, l'efficienza può essere migliore con un approccio pigro:

# Python 3 version
next(i for i, val in zip(range(len(li)-1, -1, -1), reversed(li)) if val == 'a')

# Python 2 version
from itertools import izip
indices = xrange(len(li)-1, -1, -1)
gen = izip(indices, reversed(li))
next(i for i, val in gen if val == 'a')

Un one-liner che è come Ignacio se non un po 'più semplice / chiaro sarebbe

max(loc for loc, val in enumerate(li) if val == 'a')

Mi sembra molto chiaro e Pythonico: stai cercando l'indice più alto che contenga un valore corrispondente. Non sono necessari nèx, lambda, inversioni o itertools.


Usa un ciclo semplice:

def reversed_index(items, value):
    for pos, curr in enumerate(reversed(items)):
        if curr == value:
            return len(items) - pos - 1
    raise ValueError("{0!r} is not in list".format(value))

>>> (x for x in reversed([y for y in enumerate(li)]) if x[1] == 'a').next()[0]
6

>>> len(li) - (x for x in (y for y in enumerate(li[::-1])) if x[1] == 'a').next()[0] - 1
6

def rindex(lst, val):
    try:
        return next(len(lst)-i for i, e in enumerate(reversed(lst), start=1) if e == val)
    except StopIteration:
        raise ValueError('{} is not in list'.format(val))




last-occurrence