Возвращаемые значения процедуры Python
В Python можно создать процедуру, которая не имеет явного возврата. то есть:.
def test(val):
if 0 == val:
return 8
Кроме того, можно присвоить результаты этой функции переменной:
>>> a = test(7)
>>> print `a`
'None'
Почему это так? Какая языковая логика стоит за этим непонятным дизайнерским решением? Почему это просто не вызывает ошибку компилятора?
EDIT: Да, я понимаю, что он работает именно так. Благодарю. Мой вопрос: ПОЧЕМУ? Кажется, что такой верный способ пожара ввести тонкие ошибки в ваш код. И, как было сказано ниже, e-satis, похоже, идет против очень мудрой пифонической пословицы, что "явный лучше, чем неявный".
Итак, что с этим? Является ли это просто надзором за дизайном или упрощающим предположением или преднамеренным, рассмотренным решением?
EDIT: согласны ли все с тем, что выражение этого намерения намного лучше:
def test(val):
if 0 == val:
return 8
else:
return None
Если да, то почему Python предпочитает, чтобы прежний стиль поднимал исключение времени компиляции?
РЕДАКТИРОВАТЬ: S.Lott явно указывает точку (и другие тоже делают это, как мне кажется, яснее всего ясно), что это поведение является результатом того, что Python является динамическим языком и поэтому не может проверяться при компиляции времени, времени работы системы.
Поскольку нет разграничения между процедурами (те функции, которые не возвращают значения) и функциями (теми, которые делают), что во время компиляции нечего принуждать. Это означает, что когда мы приходим к поведению во время выполнения, у нас либо есть катастрофический сбой в некоторых случаях (мы бросаем исключение), либо мы молчаем, полагая, что программист знал, что они делают, и понял поведение по умолчанию.
Питонический путь состоит в том, чтобы сделать последнее, способ стиля C - сделать первый.
Это, по-видимому, имеет смысл в качестве веской причины сделать это таким образом.
Ясное обоснование S.Lott похоронено в комментариях к принятому ответу, поэтому я подумал, что лучше всего обобщить здесь.
Я немного успокоюсь, чтобы принять ответ, чтобы узнать, дает ли S.Lott официальный ответ. В противном случае я дам очки SilentGhost.
Ответы
Ответ 1
Хотя каждая функция может не иметь явного возврата, она будет иметь неявный, то есть None
, который, кстати, является обычным объектом Python. Кроме того, функции часто return None
явно.
Я предполагаю, что возвращение None неявно является просто упрощенной оптимизацией.
P.S. Интересно, что вы предлагаете компиляции в следующем случае:
def t():
if True:
return 'ham'
Оператор P.P.S. return
указывает, что нужно вернуть , будь то None
, 42
или 'spam'
. Однако некоторые функции ничего не возвращают, например, list.sort
или __init__
, поэтому в конце каждого __init__
для накладных расходов потребуется инструкция return None
.
Ответ 2
Python никогда не проверяет человеческое поведение. Философия языка предполагает, что программисты взрослые взрослые и знают, что они делают.
Так как:
- Python - это язык с автодокументами, поэтому вы будете знать, что возвращает функцию;
- Python использует утиную печать, поэтому получение None по умолчанию может значительно облегчить вызов динамической функции.
Возврат None делает больше чувств, чем вызывает ошибку.
E.G:
function_stack = [func1, func2, func3]
for f in function_stack :
a = f()
if a is not None :
# do something
Независимо от того, f является f(), является функцией или процедурой. В Python такой вещи нет. Вы можете применить всю функцию и обработать вывод, если он есть.
Ответ 3
Хех. Подойдя к этому с точки зрения Java, ваш вопрос очевиден. Он должен выдать ошибку.
Но если вы пришли к нему с точки зрения Perl, это не очевидно. Вы устанавливаете переменную без значения, большое дело.
Это все о наборе текста. Как и Java, Python строго типизирован, но, в отличие от Java, он также динамически. Большинство динамически типизированных языков допускают такие махинации.
Ответ 4
Это красиво...
Он возвращает None
в случае, когда val != 0
, что для меня имеет смысл.
Python 2.6.1 (r261:67515, Jun 18 2009, 17:24:16)
[GCC 3.3.3 (SuSE Linux)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> def test(val):
... if 0 == val:
... return 8
...
>>> a = test(8)
>>> print a
None
>>> print test(0)
8
>>>
Есть ли у вас аргументы, почему вы считаете, что поведение неверно?
Вы можете использовать С++, если вам нужна сильная проверка типа времени компиляции, но для python она кажется чрезвычайно гибкой, и я предполагаю, что вы хотите, когда вы выбрали python для своей задачи.
Ответ 5
Какой компилятор? Компилятор байт-кода проверяет ваш код на синтаксис при импорте, но синтаксис не включает "проверить все пути для возврата". Поэтому, когда test() вызывается во время выполнения, а значение x не равно 0, и мы просто выпадали из функции, что нам делать? return 0? Почему не -1, или "", или -infinity? Поэтому хорошее нейтральное значение всегда должно возвращаться при отсутствии явного оператора return - и это значение равно None. Это стандартная функция языка - добро пожаловать на Python!
Ответ 6
Это из-за динамического ввода .
Вам не нужно проводить различие между, скажем, процедурой и функцией турбо-паскаля. Они все функции, они возвращают None
по умолчанию, что логически корректно. Если вы ничего не говорите, он ничего не возвращает, None
.
Надеюсь, теперь будет больше смысла -