Как я могу использовать строку с тем же именем объекта в Python для доступа к самому объекту? - PullRequest
10 голосов
/ 22 февраля 2012

Например, в приведенном ниже коде я хотел бы получить список [1,2,3], используя x в качестве ссылки.

In[1]: pasta=[1,2,3]
In:[2]: pasta
Out[2]: [1, 2, 3]
In [3]: x='pas'+'ta'
In [4]: x
Out[4]: 'pasta'

Ответы [ 4 ]

13 голосов
/ 22 февраля 2012

То, что вы пытаетесь сделать, это плохая практика.

Что вам действительно нужно, так это dict:

>>> dct = {'pasta': [1,2,3]}
>>> x = 'pas' + 'ta'
>>> dct[x]
[1, 2, 3]

Это право структура данных для конкретной задачи, которую вы пытаетесь достичь: использование строки для доступа к объекту.

Другие ответы предлагали (или просто показывали с беспокойством) разные способы сделать это.Поскольку Python является очень гибким языком, вы почти всегда можете найти такие разные пути для выполнения определенной задачи, но «должен быть один - и предпочтительно только один - очевидный способ сделать это» [1] .

Все они сделают свою работу, но не без недостатков:

  • locals() менее читабелен, излишне сложен и в некоторых случаях также подвержен риску (см. Mark Byers answer).Если вы используете locals(), то вы собираетесь смешивать реальные переменные с переменными базы данных, это грязно.
  • eval() довольно уродливо, это просто "-простой способ получить некоторый исходный код динамически " [2] и плохая практика .

Когда всомнение в правильности выбора, попытка следовать Zen of Python может быть началом.

И, эй, даже InteractiveInterpreter можно использовать для доступа к объекту с помощью строки, но это не значит, что я собираюсь.

2 голосов
/ 22 февраля 2012

Как и другие отмеченные, вы обычно должны избегать этого и просто использовать словарь (в приведенном вами примере) или в некоторых случаях список (например, вместо использования my_var1, my_var2, my_var3 -> my_vars).

Однако, если вы все еще хотите это сделать, у вас есть несколько вариантов.

Вы можете сделать:

locals()[x]

или

eval(x) #always make sure you do proper validation before using eval. A very powerfull feature of python imo but very risky if used without care.

Если макароны являются атрибутом объекта, вы можете получить их безопасно:

getattr(your_obj, x)
2 голосов
/ 22 февраля 2012

Ну, чтобы сделать то, что вы буквально просили, вы могли бы использовать locals:

>>> locals()[x]
[1, 2, 3]

Однако это почти всегда плохая идея.Как отметил Свен Марнах в комментариях: Храните данные вне имен ваших переменных .Использование переменных в качестве данных также может представлять угрозу безопасности.Например, если имя переменной исходит от пользователя, он может прочитать или изменить переменные, к которым вы никогда не предполагали доступ.Им просто нужно угадать имя переменной.

Было бы намного лучше использовать словарь вместо этого.

>>> your_dict = {}
>>> your_dict['pasta'] = [1, 2, 3]
>>> x = 'pas' + 'ta'
>>> your_dict[x]
[1, 2, 3]
0 голосов
/ 22 февраля 2012

Используйте это

hello = [1,2,3]
print vars()['hello']

Возвращает [1, 2, 3].

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...