У меня есть вопрос о функциях, которые имеют параметры по умолчанию.
import sys
from random import randint
my_list = [1,2,3]
def Veli(a, b = my_list):
my_list.append(randint(1,1500))
print a + b[-1]
print "Number of Refs:", sys.getrefcount(my_list)
print "Def args:", Veli.func_defaults
Veli(1) # This is 4
Veli(1) # We almost always obtain different result because of randint
Veli(1) # Again different results.
print Veli.func_defaults
print "Number of Refs:", sys.getrefcount(my_list)
Veli(1)
my_list = [-5] # old my_list has different address
print "Number of Refs:", sys.getrefcount(my_list) # Less than previous
print "Def args:", Veli.func_defaults
Veli(1) # Now gives same results.
print "Def args:", Veli.func_defaults
Veli(1) # Same result again...
Выводы: (Некоторые числа зависят от того, какие значения randint вернул, конечно.)
Количество ссылок: 3Def args: ([1, 2, 3],)3221119740([1, 2, 3, 321, 1118, 739],)Количество ссылок: 3303Количество ссылок: 2Def args: ([1, 2, 3, 321, 1118, 739, 302],)303Def args: ([1, 2, 3, 321, 1118, 739, 302],)303
Следующий код дает вам число меньше, чем предыдущий, потому что b и my_list больше не ссылаются на один и тот же адрес.
print "#ref:", sys.getrefcount(my_list) # Less than previous
Теперь у нас есть способ (единственный способ?), Чтобы достичь b,аргумент функции по умолчанию:
Veli.func_defaults[0]
Извините за мое длинное объяснение.Вот мои вопросы:
Это проблема?Словарь моего модуля раздавить переменную my_list, теперь переменная my_list имеет адрес по умолчанию, чем предыдущий.Затем функция, которая использует глобальную переменную с именем my_list в своем теле, изменяется (растет), а мой аргумент по умолчанию - нет.Почему b
не видит глобальную переменную с именем my_list
при выполнении выражения a + b[-1]
?Я знаю, b
имеет другой адрес с my_list (потому что взаимные объекты (например, список) теперь гарантированно ссылаются на другой, уникальный, недавно созданный список ), но почему Python реализован так, что b
не может видеть глобальные переменные, когда b аргументы функции?Не могли бы вы объяснить всесторонне?
Есть ли способ получить те же результаты с Veli.func_defaults [0]?Этот код выполняется, скажем, я хочу изменить параметры по умолчанию моей функции с именем Veli.Я не могу сделать это с my_list, потому что my_list и b имеют разные адреса.Одним из способов является изменение элементов списка, Veli.func_defaults [0].Есть ли другой способ (ы)?
(Это не так связано с кодом выше) Как можно получить адреса переменных?Например, как можно получить адрес b
?Я использую встроенную функцию, такую как __hash__
, но должен быть более подходящий способ.
Примечания:
a) Эти коды могут быть бесполезны по любой причине, но я хочу узнать мнения.б) Python 2.6.6 (r266: 84292, 15 сентября 2010 г., 15:52:39)[GCC 4.4.5] на linux2