Фабрис Беллар: супергерой от программирования

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

1989: LZEXE
1996: Harissa
1997: Публикация формулы Беллара для вычисления разрядов числа Пи
1999: Linmodem
2000: Вычисление самого большого простого числа (исходный код всего 438 байт)
2000: FFmpeg
2001: Компилятор TCC (Tiny C Compiler или TinyCC)
2002: TinyGL
2002: QEmacs
2003: QEMU
2004: Загрузчик TinyCC
2005: Передатчик сигнала в формате DVB-T с компьютера на телевизор
2009: Мировой рекорд по вычислению числа Пи
2011: Эмулятор компьютера с Linux на JavaScript
2011: Награжден Google-O’Reilly Open Source Award
2014: Формат сжатия изображений Better Portable Graphics (BPG)

Очень интересна программа вычисления наибольшего известного простого числа. Приведу ее полностью:

int m=167772161,N=1,t[1<<25]={2},a,*p,i,e=34893349,s,c,U=1;g(d,h){for(i=s;i<1<<
24;i*=2)d=d*1LL*d%m;for(p=t;p =(m+*p-a)*(h?1LL:c)%m,a+=*p,*p++=a%m,c=c*1LL*d%m;}main(){while(e/=2){N*=2;U=U*
1LL*(m+1)/2%m;for(s=N;s/=2;)g(17,0);for(p=t;p ;s
*--p);for(t[0]--;p>=t;)putchar(48+*p--);}

Прекрасный код, вполне в стиле acmp. На этом примере отлично видно, что Беллар может не только генерировать отличные идеи, но и оформлять их в удобные программы, которые легко читать и сопровождать.

Например, когда Беллар создал LZEXE (первый популярный упаковщик исполнимых файлов под MS-DOS), он потратил огромное количество времени, чтобы гарантировать его функциональность на разнообразных платформах, придать проекту и документации такой вид, чтобы его развитие могло взять на себя сообщество. Вся эта последующая черновая работа требует на порядок больше времени, чем написание первоначального кода.

Похоже, Беллару удалось найти некий баланс между крайностями, которые мешают продуктивной работе. Каждые несколько лет он осваивает новые области: сжатие данных, численные методы, обработка сигналов, медиаформаты, но при этом сохраняет тот же самый чистый C, уместные абстракции и приверженность открытым лицензиям.

Беллар не только программист, но и выдающийся математик, чего стоит его формула для вычисления n-ого разряда числа Пи в двоичной системе:

Выглядит максимально просто, но тем не менее ее вычислительная сложность на 43% меньше всех ранее известных формул такого типа!

The best programming language

I’ve done research and I found the best programming language of all time. You may be wondering: is it C++? or Python? or even ASM? You should be thinking: not every language is suitable for every task. They are different. And our industry is changing too fast for choosing all-time favorites. You must be skeptical: is it really possible to select a particular one to be the best?

It is possible. I have done it. Enough suspense, I’m going to say this in 3… 2… 1…

The best programming language is English.

Okay, now you’re skeptical. It’s not even for programming, you say. It’s just language. Or is it? So I’ll ask you something: do you read or write documentation? Comments? I bet you do! And I’ll tell you what: lots of useful stuff is in English only. You better know it. Do you speak with your coworkers? Do you want them to understand your ideas? If you want to work at an international company, you will have to deal with foreigners. The world is becoming increasingly more interconnected, there is no way back.

I’ll tell you more: all popular programming languages are based on English. And if you know how to write well structured English text, you know how to write good code. Because code, really, isn’t for computers. It’s for people. Good code reads like an interesting book: clear and concise, easy to understand and maintain.

Good luck with learning!

Чему не учат в универе

Постоянно слышу, что в универах плохо учат программированию. Якобы слишком много теории, которая никогда не пригодится, а вот практики маловато. Якобы зачем нам Си, если все уже давно на Питонах да на Рубях сидят. Зачем нам SQL, если реляционные базы — это уже не модно.

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

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

И это действительно плохо, когда необходимо разобраться в простейших алгоритмах. Ну это 1-2 курс, ладно. Казалось бы, на старших курсах можно уже давать большие и сложные проекты, которые нереально осилить в одиночку… но нет! Индивидуальная работа ценится превыше всего, даже диплом обычно каждый делает сам себе. А зря! Ведь работа в команде — наиважнейший навык, без которого не обойтись на любой работе.

Я считаю, что очень важно:

  1. Писать понятный код самому и уметь читать чужой код (даже если он нифига не понятный).
  2. Доходчиво излагать свою точку зрения, уметь адекватно общаться, грамотно пользоваться русским (или английским) языком. А также слушать, уметь поставить себя на место другого человека.
  3. Уметь пользоваться системами контроля версий.
  4. Соблюдать стандарты и общепринятый стиль.
  5. Быть способным оценить время, необходимое на некоторую задачу, соблюдать дедлайны (ну хотя бы примерно).
  6. Писать понятную и полную документацию.
  7. И другие, простите за выражение, гуманитарные навыки. 

И наконец, самое важное — отладка. Практически невозможно написать что-то более-менее сложное с первого раза без ошибок. Но если программист умеет быстро и качественно их отловить, то это действительно показывает его высокий уровень. Тем не менее, этому очень мало уделяется внимания. Нередки случаи, когда студенты даже не читают сообщения об ошибках (!), не говоря уж о том, чтобы посмотреть состояние стека или воспользоваться средствами отладки… Пишешь функцию — всё равно ведь будешь тестировать на каких-то данных — ну и накатай наборчик юнит-тестов, чтобы не прогонять каждый раз вручную. Несколько таких простых приемов поможет сократить уйму времени в дальнейшем. Но мало кто следует этим правилам, вот и пропускается куча ошибок в продакшн, вот и приходится потом долго и мучительно их исправлять, срывая сроки…

Так что я бы ввел побольше часов русского и английского языков (тока сразу не расстреливайте), на психологии преподавал бы что-то типа делового общения, а на старших курсах заставлял бы студентов делать большие проекты совместно.

А теория пусть остается. Ведь задача универа не только впихнуть знания, а еще и научить мыслить логически и аналитически. Как ни странно, но всякие доказательства теорем этот навык неплохо так прокачивают.

Тактильное восприятие софта

У программ и сайтов есть свои ощущения.

Проги на C++ обычно отзываются четко, кратко и сухо, всё по делу. Особенно если хорошо написаны.

С#, а также .Net в целом, ни с чем не перепутаешь. Они могут быть приятными, но вот такого ощущения непосредственного контроля, как с C++ уже нет. Кажется, что работаешь с какой-то оболочкой, прослойкой, а до самых корней добраться не дают.

А вот Java умеет как-то особенно выбешивать: даже если ничего не тормозит, все равно создается впечатление некой вязкости, как будто курсор проваливается в кнопки и там застревает. Именно поэтому я не пользуюсь продуктами многоуважаемых JetBrains, какими бы прекрасными они не были. Именно поэтому я уважаю Андроид, но телефон у меня на Symbian.

Питон и Руби во многом похожи: они оба создают впечатление мягкости, упругости и какой-то внутренней жизни. При этом Питон кажется в среднем чутка более отзывчивым.

PHP стал настолько стандартным в интернете, что никаких особых ощущений не могу заметить, он самый «обычный».

Это сложно объяснить, но работает безотказно. Бывает откроешь что-нибудь, и думаешь: «да ведь это же питон!» А потом смотришь: действительно, на питоне… А джава и дотнет на десктопе вообще с первого взгляда определяются. Вот сегодня, например, я так запалил Sublime Text (да, я поставил его только что, вот такой тормоз!) и сайт Codecademy.com. И если Sublime Text я смог сразу проверить (он правда на питоне), то насчет Codecademy я не смог так сразу найти инфу. Кто-нибудь знает, используют ли они питон или мне показалось?

Или может это вообще я один такой?

P.S. Linux и OS X в целом кажутся мне немного более вязкими, чем Windows.

Пироженка

пироженка

Что бы ты сделал, если бы узнал, что сдохнешь минут через десять (или хотя бы через день)? Напился бы? Сожрал все самое вкусное (и самое вредное) что успел бы найти? Станцевал в храме? Может украл бы годовой запас жвачки? Высказал бы окружающим всё, что о них думаешь?

Каждый придумает что-то своё, но вряд ли это будут обычные вещи, которые он совершает каждый день.

Так к чему я это завёл? Больше всего меня бесят мудаки, которые повторяют: «живи каждую минуту как последнюю» или что-то в этом роде. Если кто-то так говорит, то это лишь значит, что свои последние 10 минут жизни он проведет в попытках заебать окружающих дебильными советами.

Очевидно, мы ожидаем, что наша жизнь продолжится еще какое-то время, и действуем соответственно. Мы учимся и работаем не для себя, а для тех, кем мы станем. Мы относимся к «будущим я» как будто они наши дети. Вместо того, чтобы поддаваться сиюминутным слабостям, мы упорно работаем, делая их счастливее. Мы страдаем сегодня, чтобы будущие мы получили шанс не завалить завтрашний экзамен. Трятя 15 рублей в столовой на пироженку, мы надеемся, что они смогут насладиться угощением.  На самом деле каждый раз, когда мы чего-то хотим — чизбургер, тачку, закончить универ или жениться/выйти замуж — мы верим, что человек, которым мы станем через минуту, день, год, оценит наши поступки и порадуется унаследованному от нас миру.

Тогда какого хрена эти неблагодарные темпоральные потомки вечно остаются недовольными? Мы вкалываем и женимся, а эти твари увольняются и разводятся. Даже съев гребаную пироженку, они начинают жалеть потраченные деньги и заработанные калории… Они обвиняют нас в глупости, недальновидности и мечтают о возможности вернуться назад во времени и все исправить.

Ну и че за дерьмо тут творится? По идее мы должны лучше всех знать вкусы, предпочтения и желания людей, которыми станем через год (ну или хотя бы сегодня вечером). Разве не должны мы понимать их настолько хорошо, чтобы суметь направить свою жизнь в нужное русло? Почему же тогда вспоминая о прошлом, они чаще чувствуют сожаление, чем гордость? Я понимаю, если бы мы на них полностью забивали, но мы ведь отдаем им свои лучшие годы! Может быть, с ними что-то не так?

 

Или что-то не так с нами?

Краткое руководство по охуенности

Говорят, что есть много критериев успешности.

Но никто не скажет тебе, что большинство из них бесполезны.

Деньги, карьера, слава… что угодно. Это все, конечно, хорошо, но есть только одна вещь — реально одна — которая действительно имеет значение.

Быть охуенным.

 

Ты можешь быть бомжом и быть охуенным. Ты можешь быть полностью парализованным и быть охуенным. Да даже если ты сдохнешь, ты все равно можешь быть охуенным!

Не знаешь, в чем смысл жизни? Лови.

С этого дня твоя цель — быть самым, блядь, охуенным человеком, которого ты только можешь себе представить.

Небольшая история: у знакомой сын (ему недавно исполнилось 18 лет) купил билет на самолет куда-то за Урал на 24 дня. Из-за того, что он с какой-то чувихой оттуда переписывался, когда им было по 5 (!) лет. Мама вся в слезах, типа как я могу его отпустить, он же кроме компа ничего не знает, как же он выживет и т.п.

А что я скажу? Это охуенно! Захотелось полететь — взял и сделал.

Каких друзей ты хочешь иметь?

Какую работу?

Какой жизнью жить?

Ответ прост: ты хочешь, чтобы твои друзья, работа и все остальное было охуенным. Чем охуеннее твоя жизнь, тем счастливее ты становишься.

Серьезно, охуенность должна быть гребаной религией.

1. Ты сам.

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

Если посмотреть на меня несколько лет назад, стеснительного и нерешительного, то можно понять, что практически каждый может стать хоть чуточку круче. Например, ты.

Хотя погоди, есть еще кое-что! Что важно насчет охуенности, так это то, что она абсолютно субъективна. Тебе не обязательно заботиться о том, что я считаю охуенным, и наоборот.

Если кто-то считает, что в написании самого короткого кода на 447 задачу нет ничего охуенного, то меня просто не ебет его мнение.

Ты сам решаешь, стал ли ты круче, чем был в прошлом году.

Если так, поздравляю! Ты становишься (или уже стал) охуенным!

Но есть одна проблемка.

Это работает, только если ты честен с собой.

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

Делать что-то престижное не означает автоматически быть охуенным. Что приводит нас ко второму пункту.

2. Твои друзья.

Это те, которым на тебя не насрать. Это может быть семья, близкие друзья, девушка/парень, и даже чуваки из интернета, которых ты уважаешь (а они тебя).

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

Но опять же, слушай только тех, кто говорит тебе правду (не слушай маму).

Есть ли кто-то, на кого ты можешь рассчитывать? Тогда я советую спросить их. Найди самых охуенных людей, которых ты знаешь, и спроси их прямо сейчас.

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

Ну а если нет, я скажу тебе, как стать лучше. Быть охуенным — это твоя новая религия. Добро пожаловать в Культ Охуенности.

Хорош потреблять (в том числе информацию). Хорош сидеть вконтакте и на других сайтиках. Хорош смотреть тупые сериалы. Делай что-то. Своими руками. Снимай клипы, пиши статьи, сделай опенсорс-проект, отправься в путешествие…

Плевать на мнение людей, делай то, что нравится. То, о чем ты всегда мечтал.

Это может быть что угодно. И для этого не нужны деньги. Крутой фотоаппарат не научил еще никого снимать, а крутые кроссовки — бегать.

Охуенность это не вещи, которыми ты обладаешь, а то, что ты делаешь. Написал компилятор? Норм. Имеешь семь с половиной тысяч подписчиков на трубе? Крутяк. Ездишь на дорогой тачке? Дерьмо. Сначала докажи, что ты ее заслужил.

P.S. Я ничего не имею против крутых тачек.

P.P.S. Inspired by Julien Smith.

Boost::Spirit и друзья. Краткий экскурс. Часть 5.

BOOST_FUSION_ADAPT_STRUCT — автоматическое распространение атрибутов для пользовательских типов.

В предыдущих частях (1-я, 2-я, 3-я, 4-я) я говорил об автоматическом заполнении STL структур атрибутами при парсинге. Таким образом мы, например, заполняли список пар «ключ=значение», пользуясь тем, что сами пары могли автоматически конвертироваться в std::pair<std::string, std::string>, а список пар спокойно мог заполнить собой std::vector<std::pair<std::string, std::string> >. Весь этот механизм, как тоже было сказано ранее, основывается на том, что для стандартных контейнеров STL существуют специальные обёртки, благодаря которым они могут считаться полноценными boost::fusion последовательностями.

Как быть, если мы хотим, чтобы наша собственная структура при парсинге могла бы автоматически заполняться так же легко, как это например делают std::vector или std::string? Оказывается, способ есть. Притом достаточно простой. Я не зря сказал про обёртки, которыми снабжены стандартные контейнеры библиотеки STL. В нашем случае придётся сделать в точности то же самое — снабдить нашу структуру всем необходимым в этом плане, иными словами: сказать Boost.Fusion, что наша структура является полноправным Fusion контейнером, построенном на модели random access sequence. Специально для этого в Fusion есть макрос BOOST_FUSION_ADAPT_STRUCT, который позволяет адаптировать любую пользовательскую структуру в полноправный Fusion контейнер.

Boost::Spirit и друзья. Краткий экскурс. Часть 4.

В предыдущих частях (первая, вторая, третья) мы занимались парсингом в простые структуры данных, не сложнее обычного списка величин. Сейчас же попробуем посмотреть, как можно с минимальными усилиями строить на выходе парсера иерархические структуры данных, такие как абстрактные синтаксические деревья.

Деревья разбора и абстрактные синтаксические деревья — концепции.

Когда мы пользуемся тем или иным языком, будь то языком программирования или естественным языком, мы составляем фразы в соответствии с обпределённой иерархией подчинения. Одни смысловые конструкции включают в себя другие и сами являются составными частями более общих. Например: программа может состоять из функций; функции состоят из названия, типа возвращаемого значения, типов параметров, и исполняемого кода; исполняемый код состоит из операторов, ну и так далее.
Генерацией таких иерархических структур из текстового представления языка программирования занимается парсер. Обычно на выходе парсера мы получаем дерево разбора, то есть сущность, описывающую синтаксическую структуру программы в соответствии с описывающей её формальной грамматикой. Далее такие деревья уже преобразовываются в абстрактные синтаксические деревья (на русском) — структуры, которые избавлены от несущественных синтаксических деталей, из коих обычно состоит дерево разбора, и где присутствующие в них конструкции уже наполнены неким смысловым дополнительным содержанием, которое обычно добавляется на стадии семантического (контекстного) анализа.

Boost::Spirit и друзья. Краткий экскурс. Часть 3.

В предыдущих частях (первая, вторая) мы познакомились непосредственно с основами фреймворка для написания парсеров Spirit.Qi.
Основное время в этой части я посвящу описанию библиотеки boost::phoenix, которая в некоторых случаях очень сильно помогает облегчить написание семантических правил для грамматик, написанных на Спирите. Далее, увидим применение этого товарища на практике, сначала на демонстративных примерах, затем при реализации третьего шага нашего плана — написании компилирующего калькулятора.

Boost::Spirit и друзья. Краткий экскурс. Часть 2.

Учимся извлекать из примеров пользу. Новые друзья — атрибуты.

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