Tuesday, August 29, 2006

А мужики-то не знают ©

Оказывается, C/С++ Users Journal успешно загнулся полгода назад. Я только что из танка, да :)


Thursday, August 24, 2006

J

Настоящий гуру должен освоить три известных коммерческих языка программирования:
1. Haskell (варианты: ML/Caml/O'Caml/F#)
2. Lisp (варианты: Common lisp,scheme..)
3. APL (варианты J, K, A+)

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

Сегодня, кажется, дотянулись до J.  Во многом благодаря тому факту, что APL-like языки -- это кажется единственное, на чем можно писать из-под Pocket PC.

Вообще на PPC существуют компиляторы C, lisp, python, есть даже портированый gcc. Но после набирания первых двух строчек на python с помощью экранной клавы стилусом весь энтузиазм пропадает. А посмотрите, как красиво выглядит пересечение множеств (списков) на J:

    setintersect =: e. # [
(1 2 3) setintersect (3 4 5)
3


Monday, August 21, 2006

Декларативное программирование

В чем заключается индустрия software с технической стороны: программисты пишут программы, пользователи их покупают. Пользователям нравится, когда купленные за эти (зачастую немеряные) деньги программы работали. Желательно всегда.Потому что иначе пользователи начинают терять время и деньги, еще более немеряные. А если у пользователей деньги кончатся, программы они покупать перестанут.

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

Что является основным источником багов? Нет, не программисты, поскольку программисты тоже люди, они совершают ошибки всегда. Однако ошибки совершать намного сложнее, когда работаешь с простой и насквозь понятной системой. А непонятной и запутанной системой software становится, когда в нем появляются разного рода побочные эффекты. То есть один раз нажимаем пимпу на диалоге -- все хорошо, второй раз нажимаем --программа падает. И, главное, программисту совершенно неясно, почему -- код тот же, данные входные те же(нажатие на кнопку) -- очевидный вывод: что-то где-то изменилось и все пошло не так. Что-то -- это какая-то глобальная переменная, состояние какого-то объекта и т.п. Вникать, что именно, программист будет доолго.

Знакомая ситуация?

Посмотрим теперь на другой аспект, процесс отладки в целом. Что происходит: тестер баг наш нашел, пожаловался и сидит радуется. Что должен сделать программист: повторить баг, под отладчиком, понять, куда ставить брейкпоинт, 250 тыщ раз нажать Step Over/Step Into, следя за тем, что и куда записалось, состояние какой переменной изменилось, и че из этого вышло. Причем связи все эти "что и куда", в программе, написаной на C#/Delphi/C++/Java, нифига не очевидны и хорошо просматриваются только в динамике, когда программа запущена. Программист тратит кучу времени.

А решение этих проблем -- это декларативные, а особенно функциональные языки. Когда все логические связи очевидны, по возможности статичны и строго типизированы. Это позволяет отловить огромную часть ошибок на этапе компиляции. Более того, в таких языках по сути отсутствует понятие порядка выполнения программы. Мы просто описываем связи между данными, преобразования, а интерпретатор вычисляет ответ. Поэтому не надо дебаггером проходить всю программу. Выяснить, какая именно связь не в порядке -- в декларативном языке в разы легче, и связь эту, как правило, можно очень просто отдельно протестировать (unit тесты как будто специально придуманы для ФЯ). 

Проблемы -- во-первых, не очень высокая производительность. Но это неважно в большинстве случаев, да и есть ФЯ Ocaml который может  поспорить по скорости с C++. Во-вторых -- и это главное -- learning curve тут намного круче. Особенно для программиста, не привыкшего к такому способу мышления. Сейчас, правда, они становятся все популярнее. C# 3.0 заимствует фичи из ФЯ,  функциональный язык Nemerle становится, кажется, самой модной темой на рсдн.ру.. 

Хотя я лично в то, что "скоро не будет ни кино, ни театров, а будут сплошные ФЯ" не верю. Мейнстрим это все-таки промышленный дешевый процесс разработки software руками тысяч гастарбайтеров -- индусов, китайцев, и, может быть, русских. :) Индустриализация, промышленный переворот, от кустарного производства -- к заводам и фабрикам ПО :)
Тем не менее, сложные задачи решать на ФЯ намного удобнее. И самая большая з/п (спускаясь на землю :) -- есть и будет у людей с редкими навыками в специфических областях индустрии. Примеры успешного применения ФЯ покажу потом :)


Friday, August 18, 2006

Самый большой недостаток C++

То, что C++ -- это язык с кучей недоразумений, хаков, хаков
над хаками и т.п., я осознал уже довольно-таки давно. Но 
больше всего меня расстраивает одна вещь -- вот когда падает 
виндовс, можно ругать разработчиков. Когда интернета нету, 
я с чистой душой материть админов.

Но вот когда в C++ натыкаешься на очередные грабли, винить
вроде как некого. Страуструп, обычно, не виноват -- он писал
объектно-ориентированную обертку (читай -- "костыли") к
высокоуровневому ассемблеру под названием "C", причем это
было логично, поскольку C был сильно популярен и народ
требовал. А Дениса Ричи обвинять тоже глупо -- ну что можно
взять с ассемблера? Он создавал язык чтоб юникс писать,
низкоуровневое программирование -- порты-регистры, тут ему
просто хотелось что-то чуточку поудобнее, вот и лепил туда,
что в голову взбредет. И у него получился нормальный язык
для своей области.

Я вполне понимаю, почему C++ стал таким, какой он есть, но
вместе с этим эта вот круговая порука -- "никто не виноват" --
больше всего меня раздражает.

Нету, к сожалению, человека, чей портрет я мог бы повесить 
на рабочем месте и метать в него зубочистки ;)


Thursday, August 17, 2006

Знаете ли вы, что...

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

struct A
{
    char d :6; // ну это всем понятно
    unsigned :4; // опечатки нету ;)
    char c :10; // чему равно (x = a.c = 256) ?
    unsigned :0; // и еще фокус-покус
} a;


Pure ISO C++ :)

Отличный вопрос для собеседований, по-моему. По
крайней мере по уровню идиотизма -- самое то.

Если хотите быть language lawyer'ом, вот правильные ответы:
unsigned : 4; // просто 4 unused бита в структуре
char c : 10;  // char все равно 8 битный,
              // а два бита сверху -- просто так :)
unsigned : 0; // тут произойдет выравнивание
              // размера структуры до размера,
              // кратного allocation unit.
              // В конце структуры, правда,
              // бессмысленно это вставлять. :)


Tuesday, August 15, 2006

И еще немного о программистах

Я вдруг подумал, что во втором посте неплохо б объяснить,  что ж такое, по моему мнению, тру программер. Многие считают, что тру программеры выглядят как три гика на той заезженой фотке про вечеринку в IT стиле.
Так вот, имхо -- ничего подобного. Знакомьтесь, тру программер  John Meacham. Автор проекта jhc, компилятора языка Haskell, кто не знает -- Haskell это само по себе очень тру, нереально  круто, его знание поднимает самооценку до уровня "гуру" и  позволяет обоснованно смотреть на остальных, непосвещенных  свысока... :) (ну эту тему я думаю раскрыть в дальнейшем более подробно). 

Этот человек написал оптимизирующий компилятор языка  Haskell, что подразумевает очень глубокие познания в computer  science, теории типов, всяких там системах term rewriting и т.п. Действительно мега-программер. Действительно тру.


О программистах

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

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

Но единственное, что меня до сих пор удивляет во всем этом -- это то, как такие толпы программистов умудряются создавать сложнейшие, при этом вполне работоспособные системы, будучи при этом такими расп%*дяями ... :)