У меня есть несколько списков, имеющих все равно количество записей (каждое определение свойства объекта):
property_a = [545., 656., 5.4, 33.]
property_b = [ 1.2, 1.3, 2.3, 0.3]
...
и список с флагами той же длины
good_objects = [True, False, False, True]
(которым можно было легко заменить с эквивалентным индексным списком:
good_indices = [0, 3]
Что является самым легким способом генерировать новые списки property_asel
, property_bsel
... которые содержат только значения, обозначенные любой True
записи или индексы?
property_asel = [545., 33.]
property_bsel = [ 1.2, 0.3]
Вы можете просто использовать понимание списка :
property_asel = [val for is_good, val in zip(good_objects, property_a) if is_good]
или
property_asel = [property_a[i] for i in good_indices]
Последний быстрее, потому что good_indices
меньше, чем длина property_a
, предполагая, что good_indices
вычисляются предварительно, а не генерируются на лету.
Изменить : первый вариант эквивалентен itertools.compress
, доступному с Python 2.7 / 3.1. См. Ответ @Gary Kerr .
property_asel = list(itertools.compress(good_objects, property_a))
Я вижу 2 варианта.
Используя numpy:
property_a = numpy.array([545., 656., 5.4, 33.])
property_b = numpy.array([ 1.2, 1.3, 2.3, 0.3])
хорошие_объекты = [True, False, False, True]
хорошие_индексы = [0, 3]
property_asel = property_a[good_objects]
property_bsel = property_b[good_indices]
Используем понимание списка и застегиваем его:
property_a = [545., 656., 5.4, 33.]
property_b = [ 1.2, 1.3, 2.3, 0.3]
good_objects = [True, False, False, True]
good_indices = [0, 3]
property_asel = [x for x, y in zip(property_a, good_objects) if y]
property_bsel = [property_b[i] for i in good_indices]
Используйте встроенную функцию zip
property_asel = [a for (a, truth) in zip(property_a, good_objects) if truth]
Только что просмотрел новые возможности 2.7. В модуле itertools теперь есть функция, похожая на приведенный выше код.
http://docs.python.org/library/itertools.html#itertools.compress
itertools.compress('ABCDEF', [1,0,1,0,1,1]) =>
A, C, E, F