Функции Python I-передача аргумента

I. Аргументы по умолчанию:

Ниже приведены примеры из учебника python.org по python и моя попытка понять и объяснить, что происходит. Интерпретатор python оценивает аргументы по умолчанию только один раз, когда он читает определение функции до фактического вызова функции. Если функция вызывается снова, аргументы по умолчанию не будут снова оцениваться. Для этого приводится много причин, и вы можете прочитать ссылку на соответствующее обсуждение в конце для получения более подробной информации. В основном-

(i) Функция — это объект в Python. Он оценивается по его определению. Аргументы по умолчанию аналогичны данным члена.

(ii) имеет смысл привязывать аргументы по умолчанию при определении функции, а не при ее выполнении. (iii) Это более недорого и экономично с точки зрения эксплуатации.

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

i) Вызов функции в качестве аргумента по умолчанию:

def fn(a=someobject.somefunc())

Let us see what happens when the function returns a value that changes at runtime  every time you call it. For example time.time().

def fn(a=time.time()):
    print a

>>fn()
12:00:36

>>fn()
12:00:36

Это будет печатать одно и то же значение каждый раз, когда вызывается функция, потому что аргумент по умолчанию оценивается только один раз.

ii) Изменяемый аргумент по умолчанию, изменяемый внутри функции:

def fn(L=[]):
    L.append(1)

Давайте посмотрим на это более подробно.

def fn(a=1): #immutable default arg
    print a
    return None

>>>fn()
1

>>>fn(3)
3

>>>fn(a=2)
2
-----------------------------------------------
def fn(L=[]): #mutable list as a default arg
    print L
    L.append(1)
    print L
    return None

>>>fn()
[]
[1]

>>fn()
[1]
[1,1]

(iii) Обходной путь для изменяемого случая аргумента по умолчанию:

Если вы хотите, чтобы список инициализировался значением None каждый раз при вызове функции, вот что вам нужно сделать.

def fn(L=None):
    if L is None:
        L = []

    print L
    L.append(1)
    print L
    return None

Утверждение «если L равно None» заставляет Python переоценить значение L по умолчанию, а второе утверждение «L = []» устанавливает для него инициализированное значение. Идея состоит в том, что если вы хотите использовать изменяемые аргументы по умолчанию, всегда устанавливайте для аргумента по умолчанию неизменное значение (например, None), а затем устанавливайте его в начальное изменяемое значение внутри функции, поэтому для каждой функции вызов, который имеет значение, которое он имеет.

Вы также получите тот же результат, если сделаете следующее.

def fn(L=None):

    L = []
    print L

    L.append(1)
    print L
    return None

Вот полезная ссылка на stackoverflow для изменяемые аргументы по умолчанию .

II. Передача по ссылке:

def func1 ():
    print "Inside function func1"
    return None

def func2 (func1):
     print "Inside function func2"
     return None

>>func2()
Inside function func2

Обратите внимание, что функция func1 не выполняется до тех пор, пока она не будет явно вызвана внутри функции func2. Смотри ниже.

def func2 (func1):
     print "Inside function func2"
     a= func1()
     return None

Now func1 will be called.

>>func2()
Inside function func2
Inside function func1

III. Аргументы ключевых слов

Ожидается, что аргументы функции будут в следующей последовательности: позиционные аргументы, аргументы ключевого слова. Допустим, есть функция, которая определяется следующим образом:

def fn(a,b):
    print a,b
    return None

>>>fn(1,2)
1 2

>>>fn(2,1)
2 1

>>>D = {'a':1}

>>>tpl = (1,)

>>>fn(b=2,**D)
1 2

>>>fn(b=2,*tpl)
1 2

>>>fn(2,**D)

Error: multiple values passed for argument a (If we do not explicitly mention b=2 while passing arguments, since the first argument is 'a' in fn, it is going to expect the first val to be passed to a instead of b and then when it encounters the second argument as the unpacked dict **D (which has 'a':1), it will give error because this is the second time the value for a parameter is passed.

>>>fn(**D,2)
Will give invalid syntax since keyword arguments can only be passed in the end.

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *