Kodomo

Пользователь

Введение

Адаптационная часть этого курса посвещена тому, чтобы дать вам представление о том, что такое программирование вообще (и о том, что это не страшно, не сложно, и заодно ещё иногда и прикольно). Делать это мы будем на примере языка Python.

wtf python?

Язык Python прекрасен тем, что он находится в очень хорошем балансе между простотой самого языка и его мощностью. В этом языке есть несколько продвинутых возможностей, которые позволяют ему быть довольно широко распространённым в программистской индустрии. При этом для того, чтобы просто начать им пользоваться и получать от этого какую-то пользу, можно их не трогать, и тогда язык оказывается совсем простым.

Для python создано несколько полезных лингвистических библиотек (что это такое, мы поймём позже) и дикое море библиотек для огромного множества тем. Python весьма удобен для работы с текстами, для создания веб-сервисов, довольно пригоден для задач искуственного интеллекта. Люди, умеющие работать с python, обычно приветствуются в фирмах, имеющих отношение к компьютерной лингвистике.

python 3 vs python 2

С языком python связана одна печаль: сейчас широко распространены две версии языка – 2я и 3я. В глубине своих недров это два сильно разных языка, но на первый взгляд они кажутся почти одинаковыми. И, на наше счастье, в тех рамках, в которых мы его изучаем в адаптационной части курса, переключиться с python2 на python3 очень легко (нужно только запомнить, что в одном месте нужно ставить одну лишнюю пару скобочек), а вот в обратную сторону сложнее, там придётся отказываться от кучи удобных конструкций.

Мы будем изучать язык python3.

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

Задание 1: установить себе интерпретатор языка python

Очень просто: нужно пойти на сайт http://python.org, и найти слева ссылочку windows installer. (NB: таких ссылочки там две, нужно угадать – используя те знания, которые у вас уже есть – какая из них вам годится).

В инсталляторе можно на все вопросы отвечать Next и не задумываться.

Замечание

Начиная с этого момента в тексте много фрагментов кода на питоне. При виде КАЖДОГО фрагмента кода вы обязаны взять его, вбить в питон, и посмотреть, что питон ответит. Текст написан из предположения, что вы так и делаете.

Иначе у вас будет прекрасное ощущение, что вы всё понимаете до тех пор, пока в какой-то момент оно не сменится ощущением, что десять страниц назад вы всё понимать перестали.

Один из девизов программирования: практика – критерий истины!

Калькулятор

Язык python настолько простой, что много из него вы уже знаете:

   1 print(2 * 2)
   2 print(4 + 5 * (3 - 4))
   3 print(2 ** 8)
   4 print(abs(-3))

Эти команды очевидны и пояснений не требуют.

   1 print(5 / 2)

Когда питон имеет дело с целыми числами, он считает, что и ответ вы хотите получить в целых числах, поэтому он отбрасывает дробную часть.

Если мы хотим, чтобы питон понял, что мы имеем в виду дробное число, то в нём обязан быть десятичный разделитель. По европейской традиции это точка (а не запятая).

   1 print(5.0 / 2)

Ещё одна операция с числами – остаток от деления. Для тех, кто забыл школьный курс (а он и вправду давно был, и эта часть никому не была нужна), напоминаю, что если мы скажем питону a / b * b, то он сначала поделит a на b, отбросит дробную часть, потом помножит получившееся число на b, и в результате получит число, которое может оказаться меньше, чем a. А вот то, чего ему недостаёт, чтобы стать обратно числом a, и есть остаток от деления. Например, про 10 / 3 питон нам скажет, что ответ 3. Но 3 * 3 будет 9, а не 10. Недостающая 1 – это остаток от деления 10 на 3. Пишется в питоне это так:

   1 print(10 % 3)

Переменные

Иногда удобно запоминать промежуточные результаты. Для этого в питоне есть операция под названием "присвоение значения в переменную". Пишется она так:

   1 a = 7 * 9

Очень важно понять, что эта запись не имеет ничего общего со знаком равенства, который был в математике. В отличие от математики, это не утверждение о том, что да, эти два значения равны, а команда положить то, что справа, в переменную, которая слева. В отличие от математики, в питоне нельзя менять местами левую и правую стороны этой команды (если мы напишем 7 * 9 = a, то питон поймёт "положить в переменную 7 * 9 величину a... что? нет, вы чего-то противоестественного от меня хотите syntax error syntax error abort panic die!!!").

Второе важное замечание состоит вот в чём: на самом деле, эта команда значит "сделать так, чтобы в переменной a лежало значение 7 * 9". А если там что-то лежало до этого, выкинуть его (безвозвратно).

   1 a = 7 * 9
   2 print(a)
   3 a = 42
   4 print(a)

Как вы видите, для того, чтобы вынуть значение из переменной, нам нужно написать её имя. И в обратную сторону, всякий раз, когда мы видим просто какое-то имя переменной в тексте программы (справа от "=", если в этой строке есть "="), то это нужно читать так: "сделать то-то с тем, что сейчас лежит в переменной".

   1 b = a / 6
   2 print(b + 3)

Ещё один пример:

   1 y = 1
   2 y = y + 1

Здесь нам нужно вспомнить, что = – это операция "посчитать то, что от меня справа и положить в переменную, которая от меня слева". То есть питон сначала смотрит на правую чась выражения, и вычисляет её. В данном случае наша строка перепишется в y = 2 (с учётом, что до этого в y лежала 1), которая у нас уже не вызывает никакого удивления. Если мы эту команду повторим ещё раз, то теперь она будет значить y = 3. И т.д. То есть на самом деле эта команда читается так: положить в y число, на единицу большее, чем то, что лежало в y до сих пор. Или, ещё проще: увеличить значение y на единицу.

Строки

Ещё мы в питоне можем работать с кусочками текста. Кусочек текста называется строкой ("string") и пишется в кавычках – одинарных или двойных.

   1 print("hello")
   2 a = "world"
   3 print(a)
   4 print("hello, " + a)
   5 print(" :) " * 10)
   6 print("1")

Объекты

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

Мы можем заметить, что разные объекты ведут себя по-разному:

   1 print(1 + 2)
   2 print("1" + "2")

Это значит, что это два объекта разного типа.

Ещё одна (а на самом деле та же самая) полезная возможность – это возможность попросить питон сделать что-то с данным объектом. (Из списка того, что данный объект умеет делать). Для этого нужно написать объект точка имя действия и в скобочках аргументы – так же, как вызов функции. Такое действие над объектом называется "метод объекта".

Например, у строк есть метод "replace", которому мы говорим, что (какое слово) на что в строке заменить:

   1 x = "hello"
   2 y = x.replace("l", "LL")
   3 print(y)

Мы можем написать и так:

   1 print("hello".replace("l", "LL"))

В питоне есть специальная функция help, которая скажет про объект, какие у него есть методы, и что они делают (если авторы объекта утрудились об этом позаботиться):

   1 help(1)

Одно важное исключение про функцию help состоит в том, что хелпы про строки нужно узнавать про слово str (иначе питон пытается использовать текст строки как название темы, про которую вы хотите прочитать хелп):

   1 help(str)

Пока что только этот хелп и содержит интересные нам знания. Из него мы можем узать, что у строк есть большая гора полезных методов capitalize, который делает большой первую букву строки, а остальные маленькими, upper и lower, которые делают все буквы строки большими или маленькими, strip, которая отрезает лишние пробелы по краям, и большое море всего полезного... (Мы ещё не один раз будем смотреть пристальнее, что питон умеет делать со строками).

Замечание для бесстрашных и любопытных. На самом деле, когда мы пишем a + b, питон, прежде, чем что-либо об этой строке подумать, превращает её в a.__add__(b). Отсюда в хелпах так много функций с подчёркиваниями в именах. И отсюда и следствие, что на самом деле, вся разница поведения объектов – это разница того, какие у них есть методы и что они делают.

Слайсы

Из строк можно вырезать кусочки:

   1 x = "abcdef"
   2 print(x[3])

Это операция взять 4-ую букву из строки. Называется "индексация".

Важное замечание: в питоне нумерация букв в строке идёт с нуля, а в русском языка с единицы. В этом месте может возникать путаница, поэтому я буду всегда придерживаться очень строгой терминологии: взять n-ую букву – это по-русски, а взять букву с номером n или букву с индексом n – это по-питонски. То есть четвёртая буква – это буква с индексом 3. А прибавлять или вычитать единичку в этом случае вам придётся в уме.

Ещё можно из строки взять несколько букв:

   1 x = "abcdef"
   2 print(x[1:4])

Снова важное замечание. Когда мы берём из строки несколько букв, мы даём питону индексы, начиная с какого, и заканчивая перед каким, мы хотим брать буквы. То есть правая буква в выдаваемую строку не входит. Или, другими словами, индекс крайней правой строки, которую нам даст питон – это число после двоеточия минус один.

В большинстве случаев эта странная традиция усложняет жизнь, кроме двух.

Предположим, мы хотим в строку, между 3-ей и 4-ой буквой воткнуть "-". В питоне готовой операции для этого нет (что, к слову, печально). Поэтому нам придётся взять всё до 4-й буквы исключительно, приклеить "-", и приклеить то, что идёт с 4-й буквы включительно. И в такой формулировке это оказывается очень просто:

   1 x = "abcdef"
   2 print(x[0:3] + "-" + x[3:len(x)])

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

Дабы мы над этим не задумывались, в питоне есть полезное сокащение: если мы какое-нибудь из чисел вокруг двоеточия не указываем, то для питона это значит что мы хотели в эту сторону пойти до конца:

   1 x = "abcdef"
   2 print(x[:3] + "-" + x[3:])

Второй случай, когда оказывается полезным такой странный способ определения границ подстроки в питоне – это когда мы хотим взять первые три буквы. Можете выучить маленький приём, что сколько букв мы хотим взять, столько и нужно писать:

   1 print(x[:3] # первые 3 буквы)

Ещё одна полезная особенность питона – в нём буквы можно в строке считать не только с левого края, но и с правого. Крайная правая буква обозначается индексом минус один, вторая минус два, и т.д:

   1 print(x[-1] # последняя буква строки)

Форматирование строк

Кроме склеивания строк с помощью + и превращения чего угодно в строку с помощью str в питоне есть и ещё одно, более могучее средство формирования строк: метод format. Он предполагает такую парадигму работы: мы сначала описываем шаблон того, как в общем должна выглядеть строка, а затем заполняем шаблон значениями.

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

   1 template = "{} bottles of beer on the wall, {} bottles of beer\nTake one down, pass it around, {} bottles of beer on the wall"
   2 print template.format(99, 99, 98)

В шаблоне мы символами {} обозначаем место, куда нужно вставить очередное значение. После этого метод format получает аргументами те значения, которые нужно подставить, в том же порядке.

Внутри фигурных скобок можно указывать: что подставить в это место, и как это сделать.

В этом примере глупо повторять одно и то же значение в аргументах несколько раз. (В этом-то примере ничего страшного нет, а если мы его вычисляем, и пишем здесь в аргументе сложное выражение, или если значений становится много, то это печально). Если мы в фигурных скобках пишем число, то это число – это номер аргумента format, который мы хотим использовать. (Этот стиль нельзя совмещать в одном шаблоне с использованием просто пустых фигурных скобок). Аргументы при этом, как всегда, нумеруются с нуля:

   1 template = "{1} bottles of beer on the wall, {1} bottles of beer\nTake one down, pass it around, {0} bottles of beer on the wall"
   2 print template.format(98, 99)

За счёт этого мы получаем заодно и свободу перестановки подставляемых значений местами, что в данном примере выглядит чуточку более наглядно.

Если мы хотим подставлять числа, то мы можем делать с ними то же, что и в экселе:

Все эти параметры пишутся в фигурных скобках после двоеточия. Ширина поля задаётся просто числом: если за двоеточием идёт число, это значит, что мы хотим, чтобы данное поле занимало не менее, чем столько знаков. Например, если мы хотим, чтобы в наших стихах про бутылки все абзацы были идеально выровнены:

   1 template = "{1:2} bottles of beer on the wall, {1:2} bottles of beer\nTake one down, pass it around, {0:2} bottles of beer on the wall"
   2 print template.format(98, 99)

Мы можем выбирать несколько типов представления. Тип представления указывается буквой в самом конце внутри фигурных скобок после двоеточия:

(Их сильно больше – отсылаю вас к документации, чтобы обнаружить их).

Указывать количество знаков после десятичной точки мы можем только для дробных чисел. Синтаксис: точка и сколько знаков:

   1 template = "{1} bottles of beer on the wall, {1:.2f} bottles of beer\nTake one down, pass it around, {0} bottles of beer on the wall"
   2 print template.format(98, 99)

Это самые полезные примеры.

Ещё несколько:

   1 print "{0:6.2f}".format(42) # всего 6 знаков, из них 3 на дробную часть: точка и два знака после неё
   2 print "{0:+d}".format(42) # всегда писать + для положительных чисел (обычно пишется только - для отрицательных
   3 print "{0:06}".format(42) # заполнить пространство перед числом нулями
   4 print "{0:1}".format(42) # если величина не вписывается в требуемую длину, то оно вылезает за рамки -- так что заводите ширину всегда достаточной!

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

Experts only

Мы можем использовать подстановки и внутри самих подстановок: print "{0:{1}}".format(value, width)

Модули

Если посмотреть на сайт питона в раздел Library reference (который обозначен очень точной пометкой "keep this under your pillow"), то мы обнаружим, что питон умеет работать с неимоверной кучей чего – начиная математики и скачивания веб-страниц до работы со звуковыми файлами и базами данных. (И ещё больше возможностей есть в библиотеках, которые созданы другими авторами и распространяются отдельно).

Чтобы всё это безумное разнообразие не хранить в одном месте, оно нарезано на смысловые куски, которые называются "модули". (В других языках аналогичное понятие может быть "библиотеки", "пакеты").

Прежде, чем пользоваться модулем, мы должны питону сказать, что мы хотим им пользоваться. Например, есть в питоне модуль "math":

   1 import math

На самом деле, после того, как мы проимпротировали модуль, модуль представляется как объект, лежащий в переменной. Ииииии – мы можем узнать, какие у этого объекта есть методы!!!

   1 help(math)

Мы можем, например, обнаружить, что в модуле math есть полезные функции в духе sin, cos, sqrt и т. п.:

   1 print(math.sqrt(4))

Литература

  1. А вот свободы выбора десятичного разделителя у нас нет, только точки (1)