Проблемы с функцией GetAttr (Python 3)

У меня есть следующее в скрипте Python:

setattr(stringRESULTS, "b", b)

Что дает мне следующую ошибку:

AttributeError: 'str' object has no attribute 'b'

Кто-нибудь может сказать мне, в чем здесь проблема?

2 ответа

Решение

Не делай этого. Цитируя бесценного Грега Хьюгилла,

"Если вы когда-либо используете цитируемые имена для ссылки на переменные, обычно есть лучший способ сделать то, что вы пытаетесь сделать".

[Здесь вы на один уровень выше и используете строковую переменную для имени, но это та же самая основная проблема.] Или как С. Лотт продолжил в том же потоке:

"90% времени, вы должны использовать словарь. Остальные 10% времени, вам нужно полностью прекратить то, что вы делаете".

Если вы используете содержимое stringRESULTS в качестве указателя на некоторый объект fred который вы хотите setattrтогда эти объекты, на которые вы хотите ориентироваться, уже должны где-то существовать, и словарь - это естественная структура данных для их хранения. Фактически, в зависимости от вашего варианта использования, вы можете использовать пары ключ / значение словаря вместо атрибутов.

IOW, моя версия того, что (я предполагаю) вы пытаетесь сделать, вероятно, будет выглядеть

d[stringRESULTS].b = b

или же

d[stringRESULTS]["b"] = b

в зависимости от того, хочу ли я / нужно работать с экземпляром объекта или словарем, будет достаточно.

(PS относительно немногие подписываются на тег python-3.x. Обычно вы получите больше внимания, добавив также пустой тег python.)

Так как str является низкоуровневым примитивным типом, вы не можете установить для него произвольный атрибут. Вам, вероятно, нужен либо dict, либо подкласс str:

class StringResult(str):
    pass

который должен вести себя так, как вы ожидаете:

my_string_result = StringResult("spam_and_eggs")
my_string_result.b = b

РЕДАКТИРОВАТЬ:

Если вы пытаетесь сделать то, что предлагает DSM, т.е. изменить свойство переменной, имя которой совпадает со значением stringRESULTS переменная, то это должно сделать свое дело:

locals()[stringRESULTS].b = b

Обратите внимание, что это чрезвычайно опасная операция, которая может нанести вред вашему приложению, если вы не будете осторожны.

Другие вопросы по тегам