Mając listę liczb, w jaki sposób można znaleźć różnice między każdym ( i
) -tym elementem a jego ( i+1
) -tym?
Czy lepiej jest użyć lambda
wyrażenia, czy może zrozumienia listy?
Na przykład:
Biorąc pod uwagę listę t=[1,3,6,...]
, celem jest, aby znaleźć listę v=[2,3,...]
dlatego 3-1=2
, 6-3=3
itp
[abs(j-i) for i,j in zip(t, t[1:])]
list(itertools.starmap(operator.sub, zip(t[1:], t)))
(po zaimportowaniuitertools
ioperator
).list(map(operator.sub, t[1:], t[:-1]))
.Pozostałe odpowiedzi są poprawne, ale jeśli wykonujesz pracę numeryczną, możesz rozważyć numpy. Używając numpy, odpowiedź brzmi:
źródło
np.diff([2,4,9])
będzie[2,5]
zip
wersja?Jeśli nie chcesz używać
numpy
norzip
, możesz skorzystać z następującego rozwiązania:źródło
Możesz użyć
itertools.tee
izip
efektywnie zbudować wynik:Lub używając
itertools.islice
zamiast tego:Możesz również uniknąć korzystania z
itertools
modułu:Wszystkie te rozwiązania działają w stałej przestrzeni, jeśli nie musisz przechowywać wszystkich wyników i obsługiwać nieskończonych iteracji.
Oto kilka mikro-benchmarków rozwiązań:
Oraz inne proponowane rozwiązania:
Zauważ, że:
zip(L[1:], L)
jest równoważne zzip(L[1:], L[:-1])
ponieważzip
już kończy się na najkrótszym wejściu, jednak unika całej kopiiL
.numpy.diff
jest powolny, ponieważ musi najpierw przekonwertowaćlist
plikndarray
. Oczywiście, jeśli zaczniesz odndarray
, będzie to znacznie szybsze:źródło
islice(seq, 1, None)
zamiastislice(seq, 1, len(seq))
działać z nieskończonymi iteracjamiKorzystanie z
:=
operatora morsa dostępnego w Pythonie 3.8+:źródło
Sugerowałbym użycie
jest to proste i łatwe do odczytania.
Ale jeśli chcesz
v
mieć taką samą długość jakt
wtedylub
FYI: to zadziała tylko w przypadku list.
dla tablic numpy
źródło
Podejście funkcjonalne:
Korzystanie z generatora:
Korzystanie z indeksów:
źródło
Dobrze. Myślę, że znalazłem odpowiednie rozwiązanie:
źródło
Rozwiązanie z okresowymi granicami
Czasami w przypadku całkowania numerycznego będziesz chciał rozróżnić listę z okresowymi warunkami brzegowymi (więc pierwszy element oblicza różnicę w stosunku do ostatniego. W tym przypadku pomocna jest funkcja numpy.roll:
Rozwiązania poprzedzone zerami
Innym niedbałym rozwiązaniem (tylko dla kompletności) jest użycie
Działa jak numpy.diff, ale tylko na wektorze (spłaszcza tablicę wejściową). Oferuje możliwość dołączania liczb przed lub dołączania liczb do wynikowego wektora. Jest to przydatne podczas obsługi skumulowanych pól, które często są zmianami w zmiennych meteorologicznych (np. Deszcz, ciepło utajone itp.), Ponieważ chcesz otrzymać wynikową listę o tej samej długości co zmienna wejściowa, z pierwszym wpisem nietkniętym.
Wtedy byś pisał
Oczywiście możesz to również zrobić za pomocą polecenia np.diff, w tym przypadku musisz poprzedzić zero przed serią słowem kluczowym poprzedzającym:
Wszystkie powyższe rozwiązania zwracają wektor o tej samej długości co dane wejściowe.
źródło
Moja droga
źródło
enumerate
jest marnotrawstwem, ponieważ nie używaszvalue
. Zobacz stackoverflow.com/a/16714453/832230