Первое самое большое отличие, которое бросается в глаза - это синтаксическое выделение блоков. Традиционно, блоки в языках программирования группируются с помощью скобок (односимвольных скобок типа {} или скобок-ключевых слов типа begin/end). Автор Питона долгое время участвовал в проекте создания языка ABC, пригодного для обучения, и вынес из проекта идею синтаксического выделения блоков - отступом. В результате то, что в перле можно записать if (a eq b) { $x = 1; } в Питоне будет выглядеть
if a == b: x = 1с обязательным отступом во второй строке. В пределах блока отступ должен быть одинаков; размер табуляции жестко установлен равным 8 пробелам.
Впрочем, это не самое существенное, всего лишь синтаксические штучки.
Есть вещи куда более существенные.
Итак, Питон - современный, весьма элегантный, красивый, мощный и удобный
интерпретируемый расширяемый и встраиваемый объектно-ориентированный язык
(со множественным наследованием). Во многих аспектах это совершенно
классический процедурный язык, заимстовавший лучшие идеи из Си, Паскаля и
других языков, при этом не попавший в ловушку эклектичности. В языке есть
также элементы функционального программирования (конструкции lambda, map,
reduce).
Программы в Питоне состоят из модулей. Минимальная программа - это один
файл, содержащий инструкции.
В более сложных программах программа состоит из нескольки
файлов-модулей, которые она может использовать, импортируя из них имена.
Модули могут организовываться в иерархии каталогов и файлов. Например,
иерархия модулей XML. Если программист хочет использовать один из модулей,
его необходимо проимпортировать: import xml.sax, после чего можно
использовать: xml.sax.feed().
В отличи от перла, в котором доступностью имен управляет используемый
пакет с помощью конструкции package, в Питоне видимостью имен управляет
использующий (импортирующий) модуль. Вышеприведенную конструкцию можно
переписать в виде
from xml import sax sax.feed()или
from xml.sax import feed feed()
Первая тонкость, которую нужно помнить - во время исполнения программы существует 2 (два) пространства имен - глобальное для всего модуля, и локальное для текущей функции. Если из функции надо произвести запись в глобальную переменную, ее надо описать с помощью оператора global, например:
my_global = 0 def set_it(x): global my_global my_global = x
Если my_global - список, хэш или другая сложная структура, в которой мы хотим изменить подобъект, или my_global используется только для чтения - global не нужен.
Эти 2 пространства приводят к некоторым (победимым) неудобствам. Например, если внутри функции описана функция:
def f1(): x = 1 def f2(): y = xто f2 имеет доступ только к глобальным переменным, но не к локальным переменным функции f1. Лексической вложенности в Питоне нет. Функция lambda, создающая новую функцию, создает ее в глобальном пространстве имен.
Тонкость номер два - как Питон хранит свои объекты и позволяет программисту их именовать и использовать. В Питоне все имена переменных - это имена ссылок на объекты, а не самих объектов. Оператора присваивания в Питоне нет вообще. Есть связывание - присваивание в переменную ссылки на объект. Например, a = 1 означает: создать объект типа ЦелоеЧисло, проинициализировать его значением 1, и адрес этого объекта записать в переменную a. Чуть подробнее об этом - в следующем параграфе.
Тонкость номер три - время жизни объектов. Питон хранит для каждого объекта счетчик ссылок. При присваивании адреса объекта в переменную счетчик ссылок увеличивается, при разрыве связи - уменьшается. Когда счетчик ссылок достигает нуля - объект уничтожается. Подробный пример:
a = 1 # Создать целое число 1, и его адрес поместить в a, счетчик ссылок # равен 1 b = a # Скопировать ссылку на объект из переменной a в переменную b; # счетчик ссылок объекта увеличивается и становится равным 2 a = 2 # Создать целое число 2, и его адрес поместить в a, счетчик ссылок # равен 1; при этом Питон видит, что связь объекта разорвана, # и уменьшит счетчик ссылок объекта 1, счетчик опять станет 1, # ссылка на него есть только в b b = 2 # Создать целое число 2, и его адрес поместить в b; при этом Питон # видит, что связь объекта разорвана, и уменьшит счетчик ссылок # объекта 1, счетчик станет 0, и объект 1 будет уничтожен.
Адресной арифметики в Питоне нет, адреса можно только присваивать и
сравнивать оператором is: a is b сравнит ссылки, лежащие в двух переменных.
Соответственно, конструкций типа a += b в Питоне нет тоже - ссылкой в a
манипулировать нельзя, а для нормального сложения ссылку необходимо
разименовать: a = a + b.
Хотя переменная может ссылаться на любой объект, сами объекты имеют фиксированный тип данных. Питон - язык со строгой типизацией. В отличии от перла, число и строку сложить нельзя - надо в явном виде либо строку превратить в число, либо число в строку:
a = "1" b = 2 x = a + str(b) # => "12" y = int(a) + b # => 3
Весьма важной особенностью современных языков является обработка ошибок.
Питон предоставляет программисту оператор try и возможность определять
свои собственные исключения/ошибки.
Тонкость, связанная с исключениями и временем жизни объектов. При
возникновении исключения Питон формирует объект traceback - список на стек
фреймов; фреймы, соответственно, хранят ссылки на переменные, поэтому эти
переменные не будут автоматически удалены даже после завершения обработки
исключения. Правильным ходом является удаление объекта traceback.
Изначально в питоне исключения были строками, и это до сих пор поддерживается. но сейчас исключения - это экземпляры классов. Существует целая иерархия стандартных классов-исключений, и программист волен писать свои в любом потребном количестве. Никаких особых требований к классу-исключению не предъявляется. Класс этот может быть унаследован от любого стандартного класса, а может не иметь родительских классов вовсе.
Тонкости, связанные с типами данных.
В Питоне есть объекты неизменяемых и изменяемых типов данных. Числа, строки и n-ки - пример неизменяемых типов. Списки и хэши - изменяемые.
Еще раз: строки - неизменяемые. Если надо заменить в строке 5-ый символ, строка разбивается и пересоединяется:
s = "askjdhkfjghdf;gd" s1, s2 = s[:5], s[6:] # Индексы массивов в Питоне идут строго от нуля, к # сожалению s = s1 + 'H' + s2
Аналогом сишного null и перлового undef в Питоне является объект None. Это натуральный объект, занимающий место в памяти, имеющий тип None. Одно время в Питоне даже был баг, связанный с тем, что объект этот был изменяемым. :)
Базовый, встроенный набор функций в Питоне хоть и довольно велик, но
далеко уступает перлу. Встроенные функции предназначены в основном для
самых базовых манипуляций - проверка/преобразование типа объекта,
манипулирование с пространством имен и т.п.
Основные функции находятся в многочисленных модулях, и вот тут уже Питон
никак не уступает перлу, причем функции эти и модули структурированы по
областям применения: строковые манипуляции находятся в модуле string,
регулярные выражения - в модулях re и regex/regexp, и т.д. Питон
поставляется с большой стандартной библиотекой (часть модулей написана на
Си, а большая часть - на питоне же), и в Интернете можно найти немало
дополнительных модулей. А вот архива, эквивалентного CPAN, у Питона пока
нет :( Но будет :) И процедуры инсталляции модулей третьих сторон пока еще не
так чтобы сильно стандартизованы. Хотя и в этой области есть подвижки.
В Питоне нет интерполяции переменных. Есть аналог sprintf. То, что в перле пишется как "here $is", в Питоне будет "here %s" % is.