Як вважають інші, навряд чи використання 10 різних локальних змінних із булевими значеннями є найкращим способом написання розпорядок (особливо якщо вони справді мають однобуквені імена :)
Залежно від того, що ви робите, може бути сенсом використовувати словник замість цього. Наприклад, якщо ви хочете встановити булеві попередньо задані значення для набору однобуквених прапорів, ви можете зробити це:
>>> flags = dict.fromkeys(["a", "b", "c"], True)
>>> flags.update(dict.fromkeys(["d", "e"], False))
>>> print flags
{'a': True, 'c': True, 'b': True, 'e': False, 'd': False}
Якщо вам зручніше, ви також можете зробити це за допомогою одного заяви про призначення:
>>> flags = dict(dict.fromkeys(["a", "b", "c"], True),
... **dict.fromkeys(["d", "e"], False))
>>> print flags
{'a': True, 'c': True, 'b': True, 'e': False, 'd': False}
Другий параметр для dict
цього не повністю розроблений: він дійсно має на увазі можливість переосмислити окремі елементи словника, використовуючи такі аргументи ключових слів d=False
. Код, наведений вище, підірває результат вираження, що слідує **
за набором аргументів ключових слів, які передаються викликаній функції. Це, безумовно, надійний спосіб створення словників, і люди, здається, принаймні сприймають цю ідіому, але я підозрюю, що деякі можуть вважати це непітонічним. </disclaimer>
Ще один підхід, який, мабуть, найбільш інтуїтивний, якщо ви будете часто використовувати цей шаблон, - це визначити свої дані як список значень прапорів ( True
, False
), відображених на імена прапорів (односимвольні рядки). Потім ви перетворите це визначення даних у перевернутий словник, який відображає імена прапорців до значень прапора. Це можна зробити досить лаконічно за допомогою розуміння вкладеного списку, але ось дуже читабельна реалізація:
>>> def invert_dict(inverted_dict):
... elements = inverted_dict.iteritems()
... for flag_value, flag_names in elements:
... for flag_name in flag_names:
... yield flag_name, flag_value
...
>>> flags = {True: ["a", "b", "c"], False: ["d", "e"]}
>>> flags = dict(invert_dict(flags))
>>> print flags
{'a': True, 'c': True, 'b': True, 'e': False, 'd': False}
Функція invert_dict
- це функція генератора . Він генерує або врожає, тобто означає, що він повторно повертає значення пар - ключ-значення. Ці пари ключ-значення є оберненими змістом двох елементів початкового flags
словника. Вони подаються в dict
конструктор. У цьому випадку dict
конструктор працює інакше зверху, тому що його подають ітератор, а не словник як його аргумент.
Спираючись на коментар @Chris Lutz: Якщо ви дійсно будете використовувати це для знаків з одним символом, ви можете насправді зробити
>>> flags = {True: 'abc', False: 'de'}
>>> flags = dict(invert_dict(flags))
>>> print flags
{'a': True, 'c': True, 'b': True, 'e': False, 'd': False}
Це працює, тому що рядки Python є ітерабельними , тобто вони можуть переміщуватися через значення за значенням. У разі рядка значеннями є окремі символи в рядку. Отже, коли їх інтерпретують як ітерабельні, як у цьому випадку, коли вони використовуються у циклі for, ['a', 'b', 'c']
і 'abc'
вони фактично рівнозначні. Іншим прикладом може бути те, коли вони переходять до функції, яка займає повторення tuple
.
Я особисто не зробив би цього, оскільки він не читається інтуїтивно: коли я бачу рядок, я очікую, що він буде використаний як єдине значення, а не як список. Тож я дивлюся на перший рядок і думаю "Гаразд, значить, є Правда і Неправдивий прапор". Тож хоча це і є можливість, я не думаю, що це шлях. Наверху, це може допомогти більш чітко пояснити поняття ітерабелів та ітераторів.
Визначення функції invert_dict
такою, що вона фактично повертає словник, також не є поганою ідеєю; Я здебільшого просто цього не робив, тому що це не дуже допомагає пояснити, як працює рутина.
Очевидно, Python 2.7 має словникові розуміння, що дозволило б зробити надзвичайно стислий спосіб реалізації цієї функції. Це залишається як вправа для читача, оскільки у мене немає встановленого Python 2.7 :)
Ви також можете комбінувати деякі функції з постійно універсального модуля itertools . Як кажуть, існує більше ніж один спосіб зробити це . Зачекайте, люди Python цього не говорять. Що ж, це так чи інакше в деяких випадках. Я б здогадався, що Гвідо дав нам розуміння словника, щоб був один очевидний спосіб зробити це.