Mam fragment mojego kodu, w którym mam utworzyć centralę. Chcę zwrócić listę wszystkich włączonych przełączników. Tutaj „włączony” będzie równy, True
a „wyłączony” równy False
. Teraz chcę po prostu zwrócić listę wszystkich True
wartości i ich pozycji. To wszystko, co mam, ale zwraca tylko pozycję pierwszego wystąpienia True
(to tylko część mojego kodu):
self.states = [False, False, False, False, True, True, False, True, False, False, False, False, False, False, False, False]
def which_switch(self):
x = [self.states.index(i) for i in self.states if i == True]
Zwraca tylko „4”
x
, a potem robiłem,enumerate(x)
ale chyba wszystko, co robiłem, to wyliczanie 4? Czy to się właśnie działo? Dzięki za pomoci for i, x
ze zrozumieniem listy? Przywykłem tylko do oglądaniai for i
na przykład podobnego formatu, jaka jest funkcjax
? Dziękienumerate
Zwraca krotki (ind, value) podczas pętli, teraz możemy przypisać elementy krotki do dwóch zmiennych przy użyciu:i, x = (ind, value)
. To jest dokładnie to, co dzieje się w tej pętli.itertools.compress
roztworze, zmienićxrange
sięrange
. ( w Pythonie 3xrange
zmieniono nazwę narange
)Jeśli masz dostępne numpy:
>>> import numpy as np >>> states = [False, False, False, False, True, True, False, True, False, False, False, False, False, False, False, False] >>> np.where(states)[0] array([4, 5, 7])
źródło
np.where(states)[0]
rzeczywistego wykorzystania wynikówTL; DR : użyj,
np.where
ponieważ jest to najszybsza opcja. Opcje sąnp.where
,itertools.compress
ilist comprehension
.Zobacz szczegółowe porównanie poniżej, na którym widać, że
np.where
przewyższa zarównoitertools.compress
i równieżlist comprehension
.>>> from itertools import compress >>> import numpy as np >>> t = [False, False, False, False, True, True, False, True, False, False, False, False, False, False, False, False]` >>> t = 1000*t
list comprehension
>>> %timeit [i for i, x in enumerate(t) if x] 457 µs ± 1.5 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)
itertools.compress
>>> %timeit list(compress(range(len(t)), t)) 210 µs ± 704 ns per loop (mean ± std. dev. of 7 runs, 1000 loops each)
numpy.where
>>> %timeit np.where(t) 179 µs ± 593 ns per loop (mean ± std. dev. of 7 runs, 10000 loops each)
źródło
Możesz użyć do tego filtra:
filter(lambda x: self.states[x], range(len(self.states)))
range
Tutaj wylicza elementy listy i ponieważ chcemy tylko tych, gdzieself.states
jestTrue
, jesteśmy stosowania filtru w oparciu o ten stan.Dla Pythona> 3.0:
list(filter(lambda x: self.states[x], range(len(self.states))))
źródło
Korzystaj ze słownika,
x = {k:v for k,v in enumerate(states) if v == True}
Wejście:
states = [False, False, False, False, True, True, False, True, False, False, False, False, False, False, False, False]
Wynik:
{4: True, 5: True, 7: True}
źródło
Korzystanie z mnożenia elementów i zbioru:
>>> states = [False, False, False, False, True, True, False, True, False, False, False, False, False, False, False, False] >>> set(multiply(states,range(1,len(states)+1))-1).difference({-1})
Wynik:
{4, 5, 7}
źródło
Po prostu zrób to:
def which_index(self): return [ i for i in range(len(self.states)) if self.states[i] == True ]
źródło