пятница, 31 декабря 2010 г.

FORTH - программирования язык стековый

Введение

FORTH - весьма необычный язык программирования. Во-первых, Форт-программа записывается в постфиксной нотации, например:

2 2 + 4 = IF ... ELSE ... THEN

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

Разработка на Форте, как правило, осуществляется снизу-вверх: сначала определяются базовые слова, а затем, на их основе строятся всё более и более высокоуровневые определения. Таким образом, хорошая Форт-программа обычно состоит из большого количества маленьких слов.

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

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

Завершу своё введение короткой исторической справкой. Автором Форта является Чак Мур (Chuck Moore). Разработан язык был аж в 1960-х годах и продолжает использоваться по сей день. По задумке автора, язык должен был называться FOURTH (язык четвёртого поколения), но поскольку машина IBM 1130, на которой тогда велась разработка, допускала максимум пятизначные идентификаторы, пришлось довольствоваться FORTH-ом. Сам Чак Мур и по сей день участвует в разработке, стандартизации и внедрении Форта (http://forth.com).

FORTH на примере

В качестве примера приведу решение всем известной задачи о Ханойских башнях:
( ----------------------------------------------------------- )
( DESCRIPTION: Tower of Hanoi )
( AUTHOR: Alexander Simakov, <xdr [dot] box [at] Gmail> )
( http://alexander-simakov.blogspot.com/ )
( LICENSE: Public domain )
( HOW-TO RUN: gforth tower_of_hanoi.fs -e 'bye' )
( ----------------------------------------------------------- )


( Constants )
5 CONSTANT N_DISKS ( number of disks )
1 CONSTANT EXTRA_PAD ( extra disk padding )
250 CONSTANT DELAY ( animation delay )

( Peds )
CREATE A N_DISKS CELLS ALLOT
CREATE B N_DISKS CELLS ALLOT
CREATE C N_DISKS CELLS ALLOT

VARIABLE #MOVE_NUMBER
VARIABLE #TOTAL_MOVES

: RESET_PED ( ped_addr -- )
N_DISKS CELLS ERASE
;

: STACK_ALL_DISKS_ON_PED ( ped_addr -- )
N_DISKS 0
DO
DUP I CELLS + ( current cell address )
N_DISKS I - ( current disk number )
SWAP
! ( put next disk onto the top of the ped )
LOOP
DROP
;

: INIT_PEDS ( -- )
A STACK_ALL_DISKS_ON_PED
B RESET_PED
C RESET_PED

0 #MOVE_NUMBER !
1 N_DISKS LSHIFT 1- #TOTAL_MOVES !
;

: DISK_PADDING ( disk_number -- pad_size )
N_DISKS SWAP - EXTRA_PAD +
;

: REVERSE_DISK_INDEX ( direct_disk_index -- reverse_disk_index )
N_DISKS SWAP - 1-
;

: PRINT_DISK ( disk_number -- )
DUP DISK_PADDING SPACES ( left padding )
DUP
2 * 0
?DO
[CHAR] = EMIT
LOOP
DISK_PADDING SPACES ( right padding )
;

: PED_LABEL_PADDING ( -- )
N_DISKS 2 * 2 - 2 / EXTRA_PAD +
;

: PRINT_PED_LABEL ( ped_label -- )
PED_LABEL_PADDING SPACES
[CHAR] # EMIT
EMIT
PED_LABEL_PADDING SPACES
;

: PRINT_PED_LABELS ( -- )
[CHAR] A PRINT_PED_LABEL
[CHAR] B PRINT_PED_LABEL
[CHAR] C PRINT_PED_LABEL
;

: PRINT_STATS ( -- )
." Move number/total moves: "
#MOVE_NUMBER @ .
." / "
#TOTAL_MOVES @ .
;

: PRINT_PEDS ( -- )
PRINT_STATS CR
N_DISKS 0
DO
CR
A I REVERSE_DISK_INDEX CELLS + @ PRINT_DISK
B I REVERSE_DISK_INDEX CELLS + @ PRINT_DISK
C I REVERSE_DISK_INDEX CELLS + @ PRINT_DISK
LOOP
CR
PRINT_PED_LABELS
;

: REFRESH_PEDS ( -- )
PAGE
PRINT_PEDS
DELAY MS
;

: GET_TOP_DISK_ADDR ( ped_addr -- top disk addr )
DUP N_DISKS 1- CELLS + ( top ped addr )
BEGIN
DUP @ IF NIP EXIT THEN
1 CELLS -
2DUP >
UNTIL ( until start addr > cur addr )
ABORT" Ped is already empty"
;

: GET_FREE_SLOT_ADDR ( ped_addr -- free slot addr )
DUP N_DISKS 1- CELLS +
SWAP
BEGIN
DUP @ 0= IF NIP EXIT THEN
1 CELLS +
2DUP < ( until end addr < cur addr )
UNTIL
ABORT" Ped is already full"
;

: MOVE_DISK ( from_ped to_ped -- )
GET_FREE_SLOT_ADDR SWAP
GET_TOP_DISK_ADDR SWAP
OVER @ SWAP ! ( copy disk to new ped )
0 SWAP ! ( remove disk from old ped )
1 #MOVE_NUMBER +! ( increment move number )
;

: TOWER_OF_HANOI ( from_ped to_ped tmp_ped n_disks -- )
RECURSIVE

DUP 1 = IF
2DROP
MOVE_DISK
REFRESH_PEDS
EXIT
THEN

3 PICK ( push from_ped )
2 PICK ( push tmp_ped )
4 PICK ( push to_ped )
3 PICK 1- ( push n_disks-1 )

TOWER_OF_HANOI

3 PICK ( push from_ped )
3 PICK ( push to_ped )

MOVE_DISK
REFRESH_PEDS

1 PICK ( push tmp_ped )
3 PICK ( push to_ped )
5 PICK ( push from_ped )
3 PICK 1- ( push d_disks-1 )

TOWER_OF_HANOI

2DROP
2DROP
;


INIT_PEDS
REFRESH_PEDS
A C B N_DISKS TOWER_OF_HANOI
CR

Скачать файл: tower_of_hanoi.fs

Для запуска можно использовать GNU Forth:
gforth tower_of_hanoi.fs -e 'bye'
Также имеется анимация в виде консольного ролика tower_of_hanoi_animation.ttyrec. Для его воспроизведения понадобится пакет ttyrec:
ttyplay tower_of_hanoi_animation.ttyrec
Заключение

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

Ссылки

суббота, 20 ноября 2010 г.

Язык APL: разминка для ума

Введение

Язык APL, разработанный в IBM Кеннетом Иверсоном (Kenneth Iverson) и Эдином Фалкоффом (Adin Falkoff), примечателен по многим причинам. Во-первых, ему уже почти 50 лет. Во-вторых, первые 7-8 лет разработка велась вообще без компьютеров, на бумажке. В те времена язык называли не иначе как нотацией Иверсона. Название APL появилось позже, когда в 1962 Иверсон опубликовал книгу под названием "A Programming Language". Ещё один удивительный факт - наличие собственного ни на что не похожего набора символов, для ввода которых использовалась специальная APL-клавиатура. В четвёртых, новаторская по тем временам технология работы со сложными иерархическими структурами данных.

Поскольку сам язык ориентирован на работу с массивами (в том числе и многомерными), в грамотно-написанной программе на APL редко встречаются циклы и "возня" с отдельными элементами. Наличие специфической нотации и очень высокоуровневых даже по современным меркам операций, позволяет запрограммировать в однострочнике на APL то, на что в другом языке потребовало бы целой программы. От некоторых таких "шедевров", незнакомый с APL-ем программист вполне может временно впасть в оцепенение. Один из ярких примеров - реализация знаменитой математической забавы известной как Game of Life. Реализация игры на Dyalog APL, одном из современных диалектов APL-я, приводится в википедии.

Посмотреть

Вообще, изучение незнакомых языков, пусть даже и весьма поверхностное, существенно расширяет кругозор. А знакомство с APL-ем бесспорно стоит потраченного времени. Посмотреть за тем как гуру пишет и объясняет однострочник для Game of Life на Dyalog APL можно тут.

Диалект APLX, который использовался мной для экспериментов с APL-ем несколько отличается от Dyalog'а. Иначе определяются функции и нет некоторых операторов. Моё видео - "Game of Life на APLX" не столь захватывающе как предыдущее, но всё же имеет право на существование:



А вот, собственно, основное заклинание:

Попробовать

С сайта APLX можно скачать бесплатную версию для некоммерческого использования под Linux и Windows. С сайта Dyalog APL на аналогичных условиях доступна версия для Windows.

Ссылки

воскресенье, 24 октября 2010 г.

Идеальная архитектура. Ведущие специалисты о красоте программных архитектур

Идеальная архитектура. Ведущие специалисты о красоте программных архитектур // 2010
Диомидис Спинеллис, Геориос Спинеллис

Эта книга состоит из набора более или менее связанных статей, написанных различными авторами о проектах, в которых они принимали активное участие. Начинать читать можно смело со второй главы, так как первая глава - "Что такое архитектура?" - чрезвычайно разжижена досужими разговорами и абстрактными определениями не менее абстрактных понятий.

Значительную часть книги составляют статьи об архитектуре различных систем виртуализации и эмуляции: Xen (гипервизор), JPC (эмулятор x86, написанный на Java), Jikes RVM (научно-исследовательская виртуальная машина Java, написанная на Java и работающая под управлением самой же себя). Из более экзотических вещей можно отметить обзор архитектуры OpenSource фреймворка для создания онлайн (Massive Multiplayer Online) игр под названием Darkstar (опять же на Java).

Очень любопытные статьи про GNU Emacs и KDE: в них рассматриваются не только архитектурные изюминки данных систем, но и описывается социальное устройство этих известных и славных OpenSource проектов.

К сожалению, при всей своей архитектурной красоте и современности, некоторые проекты развиваются не очень активно. Так, например, обстоят дела с проектом JPC. Судя по данным с сайта проекта, полноценная поддержка (т.е. загрузка до графического режима) есть только для DOS и двух специализированных Linux-дистрибутивов (Damn Small Linux и Feather Linux). Ни Debian ни Ubuntu ни RedHat ни даже Windows XP не поддерживаются. Зато можно поиграть в старый добрый DOS-овский DOOM прямо в апплете браузера и лишний раз подивиться красоте архитектуры и смелости замысла.

С проектом Darkstar всё тоже не так гладко. Ранее этот проект поддерживало подразделение Sun Labs, но видимо в связи с недавней покупкой Sun-а Oracle-ом проект прикрыли. Не смотря на это, от Darkstar-а отпочковался проект RedDwarf, который поддерживается теперь самим сообществом.

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

Оценка по шкале ИМХО: 4

пятница, 15 октября 2010 г.

Автодополнение имён Perl-модулей в Bash

Введение

Автодополнение имён файлов и директорий в Bash - настолько удобная и полезная функция, что пальцы сами тянутся нажать на [TAB] для получения списка вариантов или точного совпадения. Это экономит массу времени и уменьшает вероятность опечатки. Однако, возможности автодополнения в Bash не ограничиваются только лишь именами файлов и директорий: по-сути, автодополнять можно любую команду причём совершенно произвольным образом.

В этой статье рассказывается о том, как научить Bash автодополнять имена Perl-модулей. Вот только несколько возможных применений этой функции:
  • Вывод документации по модулю (perldoc My::Modu [TAB] My::Module)
  • Редактирование модуля (vim Foo::B [TAB] Foo::Bar)
  • Вывод версии модуля (см. pm-version.pl)
По большей части эти преимущества оценят люди, ежедневно занимающиеся разработкой на Perl. Остальные же могут изучить этот пример и адаптировать его для своих нужд.

Получение списка модулей

Во-первых, нам понадобится скрипт, позволяющий получить имена всех Perl-модулей, установленных в системе. Для этой цели прекрасно подходит pmdesc3.pl который, кстати, входит в состав perl-support.vim - отличного VIM-плагина для Perl-разработчиков. Помимо имени модуля, этот скрипт также выводит его версию и заголовок POD документации:
./pmdesc3.pl

...
WWW::Mechanize (1.34) Handy web browsing in a Perl object
WWW::RobotRules::AnyDBM_File (5.810) Persistent RobotRules
DateTime::TimeZone (0.7701) Time zone object base class and factory
DateTime::Locale (0.35) Localization support for DateTime.pm
...
Эта дополнительная информация будет лишней при выводе списка совпадений в Bash-е, поэтому её лучше предварительно убрать:
./pmdesc3.pl 2>/dev/null | awk '{ print $1 }' > /path/to/modules.list

...
WWW::Mechanize
WWW::RobotRules::AnyDBM_File
DateTime::TimeZone
DateTime::Locale
...
Таким образом, в файле /path/to/modules.list окажется список всех установленных модулей. Этот список следует поддерживать в актуальном состоянии: обновлять cron-задачей, а также сразу после установки нового Perl-модуля (читай ниже).

Важный момент: для того чтобы скрипт pmdesc3.pl нашёл не только стандартные модули, но и модули написанные вами, следует добавить соответствующие пути к переменной окружения PERL5LIB:
PERL5LIB="$PERL5LIB:/path/to/my/lib/"
Напомню, что обычно, переменные, определённые в ~/.bashrc не наследуются cron-задачами, поэтому соответствующую переменную необходимо прописать и в crontab-е.

И, наконец, финальное замечание. Как оказалось, скрипт pmdesc3.pl не посещает директории из @INC, являющиеся символическими ссылками на другие директории. К примеру, в Debian Lenny:
$ ls -l /usr/share/perl/5.10
lrwxrwxrwx 1 root root 6 Фев 11 2009 /usr/share/perl/5.10 -> 5.10.0
Но не смотря на то, что в @INC есть /usr/share/perl/5.10, директория /usr/share/perl/5.10.0 скриптом не обрабатывается. Для того чтобы скрипт обошёл и "символические" директории тоже, добавьте их явно к PERL5LIB.

Настройка автодополнения

Механизм автодополнения работает следующим образом. Пользователь определяет специальную функцию и регистрирует её командой complete. В результате, complete связывает конкретную команду (в нашем примере их три: V, v и d) с пользовательской функцией для автодополнения (_perl_module). Почему названия команд такие странные, вскоре станет ясно. Пока же можно считать, что для лаконичности.
PERL_MODULES_LIST="/path/to/modules.list"

_perl_module() {
COMPREPLY=();
cur="${COMP_WORDS[COMP_CWORD]}"

if [[ ${cur} == ?* ]] ; then
COMPREPLY=( $(grep "^${cur}" "$PERL_MODULES_LIST" | sed -e 's/:/\\:/g') )
return 0
fi
}

complete -F _perl_module V
complete -F _perl_module v
complete -F _perl_module d
Функция автодополнения получает в качестве аргумента часть уже введённого текста ($cur) и на его основе должна сохранить в переменной COMPREPLY список вариантов. В нашем случае это результат элементарного grep-а по имени модуля плюс экранирование символа ':'. Экранирование несколько портит вид выводимой подсказки, но к сожалению без этого нельзя.

Отмечу, что более сложная функция автодополнения может использовать контекст (предыдущие введённые слова) для более интеллектуальной подсказки. К примеру, предыдущее слово можно получить так:
prev="${COMP_WORDS[COMP_CWORD-1]}"
Приведённый выше файл необходимо поместить туда, где Bash сможет его найти и загрузить. В Debian Lenny есть специальная директория для функций автодополнения: /etc/bash_completion.d/

Bash-алиасы

Алиасы d и V, упомянутые выше, названы так только для краткости. Для того чтобы они заработали необходимо добавить в ~/.bashrc следующие строки:
alias d="perldoc"
alias V="/path/to/pm-version.pl"
Скрипт pm-version.pl показывает версию модуля и сообщает является ли он core-модулем и если да, то начиная с какой версии Perl.
alias v="PAGER=$EDITOR perldoc -m"
Алиас v - немного хитрее. Он позволяет открывать Perl-модули на редактирование по имени, а не по пути, т.е. v Foo::Bar вместо vim /path/to/lib/Foo/Bar.pm

Для достижения этой цели используется малоизвестная опция -m команды perldoc. С этой опцией perldoc открывает код Perl-модуля (не POD, а именно код!) пейджером (обычно less). Подставив в PAGER ваш любимый $EDITOR, исходный код модуля чудесным образом откроется на редактирование.

Обновление списка модулей при установке нового пакета

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

Обычно, во всех дистрибутивах имена пакетов для Perl-модулей имеют определённую структуру. В Debian, к примеру, за очень редким исключением, пакет для Perl-модуля Foo::Bar будет называться libfoo-bar-perl. Используя этот факт несложно написать небольшую обёртку для менеджера пакетов, которая будет выполнять следующие действия:
  • Преобразование имени Perl-модуля в имя пакета
  • Установку пакета
  • Пересоздание или обновление списка установленных модулей
Интеграция с VIM-ом

Как известно, VIM имеет встроенный механизм автодополнения по словарю (CRTL+n). Таким образом, если подключить уже имеющийся у нас список модулей в качестве словаря, то можно будет автодополнять выражения вида use и require:
use Foo::B [CTRL+n]
| Foo::Bar
| Foo::Bar::Baz
Вот необходимое заклинание для ~/.vimrc:
set dictionary+=/path/to/perl-modules.list
Консольный скрин-каст: сёрфинг по Perl-модулям

Работу автодополнения наглядно демонстрирует следующий консольный ролик: surf-perl-modules.txt. Для его воспроизведения потребуется программа ttyplay:
ttyplay surf-perl-modules.txt
Приятного просмотра!

Ссылки

пятница, 20 августа 2010 г.

Создание PDF-файлов на Perl

Введение

Начну с того, что есть несколько различных подходов к решению данной задачи:
  1. Создание PDF "с нуля" (PDF::API2, PDF::Haru, PDF::CreateSimple)
  2. Модификация уже существующего PDF-бланка (PDF::Reuse, PDF::API2, PDF::Haru, PDF::CreateSimple)
  3. Создание PDF из XML-шаблона при помощи XSLT-преобразования (XML::ApacheFOP)
  4. Конвертация LaTeX или HTML файла в PDF внешними утилитами (исходые файлы при этом можно генерировать по шаблону, к примеру, Template::Toolkit)
У каждого подхода есть свои плюсы и минусы, так что выбор зависит от конкретной ситуации. В этой же статье четь пойдёт о первом подходе, а точнее о создании PDF-файлов при помощи модуля PDF::API2.

Краткий обзор PDF::API2

Модуль PDF::API2 - ветеран среди PDF-модулей на CPAN. Проект насчитывает уже несколько лет и обладает внушительным функционалом. Стоит отметить, однако, что интерфейс PDF::API2 довольно запутан и не всегда очевиден, кроме того, работать придется с довольно низкоуровневыми элементами (графические примитивы, строки текста и т.д.). Последний недостаток отчасти компенсируют модули-обёртки с более удобным интерфейсом: PDF::API2::Simple, PDF::Table.

В целом, работа с PDF::API2 напоминает рисование: получить графический контекст, задать необходимые атрибуты (цвет, фон, стиль начертания), вызвать соответствующий метод-примитив (текст, прямоугольник, дуга и т.д.).

Ниже приводится небольшой скрипт для создания минимального PDF-файла. Следующим шагом рекомендую ознакомиться с отличным tutorial-ом по данной теме: Using PDF::API2. Ну а осилив и его, можно уже открывать документацию по PDF::API2. Итак, пример:

Пример

#!/usr/bin/perl

#===============================================================================
#    REVISION:  $Id$
# DESCRIPTION:  Минимальный пример использования PDF::API2
#      AUTHOR:  Alexander Simakov, <xdr (dot) box (at) Gmail>
#               http://alexander-simakov.blogspot.com/
#     LICENSE:  Public domain
#===============================================================================

use strict;
use warnings;

our $VERSION = qw($Revision$) [1];

use Readonly;
use PDF::API2;

# Размер бумаги A4
Readonly my $PAGE_WIDTH  => 210;
Readonly my $PAGE_HEIGHT => 297;

# Внутренняя единица измерения PDF::API2 - пункты
# см. http://ru.wikipedia.org/wiki/Типографский_пункт
Readonly my $ONE_MILLIMETER_IN_POINTS => 72 / 25.4;

# Перевод миллиметров в типографские пункты
sub _mm_to_pt {
    my $mm = shift;

    return $mm * $ONE_MILLIMETER_IN_POINTS;
}

sub main {

    # Создаём PDF-объект
    my $pdf = PDF::API2->new( -file => 'example.pdf' );

    # Создаём новую станицу размера A4
    my $page = $pdf->page();
    $page->mediabox( _mm_to_pt($PAGE_WIDTH), _mm_to_pt($PAGE_HEIGHT) );

    # Встраиваем в PDF-файл шрифты
    my %fonts = (
        Helvetica => {
            Bold   => $pdf->corefont('Helvetica-Bold'),
            Roman  => $pdf->corefont('Helvetica'),
            Italic => $pdf->corefont('Helvetica-Oblique'),
        },
    );

    # Напишем строку текста
    my $text_ctx = $page->text();

    $text_ctx->font( $fonts{'Helvetica'}{'Bold'}, 12 );
    $text_ctx->fillcolor('red');

    # В PDF::API2 - начало координат в левом нижнем углу
    $text_ctx->translate(
        _mm_to_pt( $PAGE_WIDTH / 2 ),
        _mm_to_pt( $PAGE_HEIGHT / 2 )
    );

    # Выводим строку с выравниванием по центру
    $text_ctx->text_center('Hello PDF::API2');

    $pdf->save();

    return;
}

main();

А вот результат: example.pdf
Скачать скрипт: create_example_pdf.tar.gz

Заключение

Модуль PDF::API2 позволяет достаточно тонко и точно контроллировать процесс создания PDF-файла, но за всё приходится платить. В данном случае плата - это довольно большое количество усилий необходимых для выполнения относительно простых операций.

Ссылки

среда, 11 августа 2010 г.

Программист-прагматик. Путь от подмастерья к мастеру

Программист-прагматик. Путь от подмастерья к мастеру // 2009
Эндрю Хант, Дэвид Томас

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

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

Оценка по шкале ИМХО: 5

пятница, 6 августа 2010 г.

pm-version.pl --- самый быстрый способ узнать установлен ли Perl модуль и если да, то какой версии

Введение

Для того чтобы узнать установлен ли определенный Perl модуль, чаще всего пишут короткий однострочник, который загружает модуль и распечатывает его $VERSION. Ниже представлен усовершенстованный вариант который помимо вывода версии, проверяет является ли модуль встроеным и если да, то начиная с какой версии Perl. Для максимальной эффективности предлается установить короткий Shell alias (см. в заголовке скрипта) для вызова pm-version.pl

Примеры
V Smart::Comments
Smart::Comments v1.0.3

V File::Spec
File::Spec v3.2501 (built-in since perl v5.00405)

V Foo::Bar
Foo::Bar is not installed

Скачать
http://entropyware.info/blog/perl_tools/pm-version.tar.gz

пятница, 23 июля 2010 г.

Changelists в Subversion

Начиная с версии 1.5 в Subversion появилась поддержка функции Changelists. Данная функция позволяет группировать файлы в рабочей копии путём присвоения им произвольных текстовых ярлычков. Полученные таким образом "групповые имена" можно передавать командам commit, diff, update и другим вместо непосредственного списка файлов.

Changelists особенно удобны если требуется, к примеру, за-commit-ить два набора файлов, но непременно по-отдельности. Предположим, новые функции в одном, а исправления ошибок в другом. Разумеется, можно держать и в голове, какие файлы каким commit-ом должны пойти, но лучше приберечь энергию для более важных дел и поручить скучную рутину Changelists:
svn changelist new-features foo.pl bar/baz.pl
Path 'foo.pl' is now a member of changelist 'new-features'.
Path 'bar/baz.pl' is now a member of changelist 'new-features'.

svn changelist bug-fixes quux.pl
Path 'quux.pl' is now a member of changelist 'bug-fixes'.

svn status
--- Changelist 'new-features':
M bar/baz.pl
M foo.pl

--- Changelist 'bug-fixes':
M quux.pl

svn commit -m "New cool functions" --changelist new-features
Sending bar/baz.pl
Sending foo.pl
Transmitting file data ..
Committed revision 3.

svn commit -m "Bug fixes" --changelist bug-fixes
Sending quux.pl
Transmitting file data .
Committed revision 4.
При этом надо помнить, что Changelists в Subversion имеют несколько особенностей:
  • нельзя навесить два ярлыка на один и тот же файл
  • нельзя навесить ярлык на директорию
  • Changelists - это свойство локальной копии, а не репозитория
Подробности можно получить на соответствующей странице руководства Subversion: http://svnbook.red-bean.com/en/1.5/svn.advanced.changelists.html

вторник, 20 июля 2010 г.

perlcritic-checker v1.2.1 released

What's new
  • Make tests more friendly for CPAN Testers
  • Corrections in POD
How to get

среда, 14 июля 2010 г.

Higher-Order Perl: Transforming Programs with Programs

Higher-Order Perl: Transforming Programs with Programs // 2005
Mark Jason Dominus

Пожалуй каждому программисту знаком принцип DRY - Don't Repeat Yourself. Систематическое нарушение этого правила ведёт к тому, что с ростом проекта поддерживать и развивать его становится всё сложнее и сложнее. Очевидное решение - выискивать повторяющиеся или похожие фрагменты кода и устранять их вводя дополнительные уровни абстракции.

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

Как и большинство хороших книг по программированию (а может быть и не только по программированию) эта книга "многослойная". Довольно трудно осмыслить и опробовать весь материал всего за одно прочтение. Однако освоение даже самого верхнего "слоя" позволит думать на Perl уровнем выше.

Оценка по шкале ИМХО: 5

среда, 16 июня 2010 г.

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

Путь камикадзе. Как разработчику программного обеспечения выжить в безнадежном проекте // 2001
Эдвард Йордон

Под безнадёжным, Йордон понимает такой проект, который либо чрезмерно ограничен по срокам либо по бюджету (читай - практически любой проект). Понятно, что такой проект неизбежно потребует от команды сверхурочной работы. Если при этом проект рассчитан на несколько десятков человеко-лет, то изнурительные и регулярные переработки и ночные бдения вполне могут подорвать здоровье, ввести в состояние депрессии и даже разрушить семью. Автор задаётся резонным вопросом - а оно того стоит? Что читается между строк пламенной героической речи высокого руководства? Каковы их истинные мотивы?

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

Оценка по шкале ИМХО: 4

воскресенье, 6 июня 2010 г.

perlcritic-checker v1.2

Описание

perlcritic-checker это Subversion pre-commit hook, который проверят Perl-код с помощью модуля Perl::Critic. Если передаваемый код содержит нарушения, то весь коммит будет отвергнут. Этот инструмент предназначен для внедрения единых практик кодирования в команде разработчиков.

Что нового в версии 1.2
  • progressive mode
    В прогрессивном режиме perlcritic-checker не ругается на существующие нарушения, но препятствует внесению новых. Эта опция идеально подходит для уже существующих крупных Perl-проектов, которые разрабатывались без оглядки на рекомендации из книги Perl Best Practices.
  • emergency commits
    Бывают ситуации когда нет времени устранять нарушения: код требуется закоммитить немедленно. В этом случае достаточно включить в комментарий коммита ключевое слово "NO CRITIC". Например, svn commit -m "NO CRITIC: Emergency bugfix" Foo.pm
    Такой коммит обойдёт все проверки.
  • test suite
    Теперь работоспособность perlcritic-checker'а можно проверить при помощи тестов
Как скачать

Проект perlcritic-checker наконец-то обрёл свой дом:

Дистрибутив также доступен на CPAN:

Ещё по теме

пятница, 21 мая 2010 г.

97 этюдов для архитекторов программных систем

97 этюдов для архитекторов программных систем // 2009
Нил Форд, Майкл Найгард, Билл де Ора и др.

Редкий случай когда название книги в переводе точнее отражает её суть нежели оригинал. В английском варианте книга называется "97 Things Every Software Architect Should Know", что производит впечатление структурированности и целостности. На самом деле это коллективный труд группы известных архитекторов ПО состоящий из 97-ми независимых статей-этюдов. Примечательно, что каждый этюд занимает от полутора до двух страниц текста, что позволяет ему полностью уместиться на одном книжном развороте. Такая организация материала крайне удобна когда читаешь книгу не "от корки до корки", а минут по 15-20 в день.

Что касается содержания, то ожидать чего-то фундаментально-нового и прорывного стоит едва ли. В целом, все гуру-архитекторы призывают своих собратьев по профессии к простоте дизайна, сдержанности идей и личной скромности. Последнему вопросу уделяется особое внимание, так как архитекторы ПО нередко "обожествляют" свою профессию, дистанцируясь тем самым от простых работяг-программистов.

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

Ещё один отзыв

Оценка по шкале ИМХО: 4

понедельник, 29 марта 2010 г.

Perl Medic: Transforming Legacy Code

Perl Medic: Transforming Legacy Code // 2004
Peter J. Scott

Не секрет, что львиную долю своего времени программисты тратят на поддержку и доработку уже существующего кода. В самом простом случае - это собственный код, написанный некоторое время назад. Поддерживать такой код даже приятно. Если код был написан другими людьми, то разобраться в нём - задачка посложнее. Для большей правдоподобности, предположим, что первоначальный автор программы давно уволился и сейчас недоступен. Ах, да, ещё выяснилось, что для программы которую вам нужно будет поддерживать и изменять нет ни тестов ни документации, плюс ко всему, development-окружения в котором была бы продублирована система попросту нет - рабочая система существует лишь в production-среде и то в единственном экземпляре. Правда весело? Вот вкратце мизансцена которую приводит автор книги. Конечно, не всегда всё так плохо, но лучше быть готовым к худшему сценарию.

Итак, эта книга о том, как сделать чужой Perl-проект своим и постепенно привести его в божеский вид. В целом, книга довольно интересная и построена вокруг реальных жизненных ситуаций, однако многое из того, что в 2004-м году было новаторством, сейчас либо перешло в категорию прописных истин (к примеру, возьмите use strict за правило) либо стало банальным фактом (тесты, тесты и ещё раз тесты), описанным во множестве других книг. Тем не менее, даже сейчас из этой книги всё ещё можно почерпнуть что-то новое и полезное.

Оценка по шкале ИМХО: 4

пятница, 26 марта 2010 г.

CDArgs - перемещение по файловой системе со скоростью света

CDArgs - это утилита, способная существенно повысить и без того очень высокий уровень жизни обитателей консоли. При помощи CDArgs и набора Shell-функций, идущих с ней в комплекте, можно легко создавать закладки на директории в файловой системе и очень быстро по ним перемещаться. Каждой закладке можно назначить короткое имя и использовать его в дальнейшем для перехода в соответствующую директорию. Самое приятное, что по именам закладок работает автодополнение точно также как это происходит с обычной командой cd.

Для настройки CDArgs необходимо выполнить следующую процедуру:
  • Установить соответствующий пакет
  • Добавить в .bashrc трехстрочную функцию cv (её исходный текст есть cdargs(1))
  • Включить (source) в .bashrc содержимое файла cdargs-bash.sh с дополнительными функциями и автодополнением (полный путь к файлу в вашей системе опять-же смотрите в cdargs(1))
Из дополнительных удобств, определяемых в cdargs-bash.sh, следует отметить функцию mark [bookmark_name], которая добавляет текущую директорию в список закладок, а также обёртки для команд cp и mv, которые принимают имена закладок вместо имен директорий. Тем кто вместо Bash использует другой shell, расстраиваться не стоит - в cdargs(1) описаны настройки и для других оболочек.

В заключение, небольшой консольный screen-cast использования CDArgs, записанный при помощи ttyrec: cdargs-demo.txt. Для воспроизведения запустите:
ttyplay cdargs-demo.txt

вторник, 2 марта 2010 г.

Programming Web Services with Perl

Programming Web Services with Perl
Pavel Kulchenko, Randy J. Ray

Как ни печально, но это чуть ли ни единственная книга по программированию веб-сервисов на Perl. Печально прежде всего от того, что книга была издана аж в 2002 году. Понятно, что за 8 лет в такой популярной и динамично развивающейся области как веб-сервисы очень многое успело измениться.

Перспективы Perl-модуля SOAP::Lite, вокруг которого главным образом и построена книга, также не внушают оптимизма. Вот что по этому поводу говорит текущий мэйнтейнер SOAP::Lite:
Therefore SOAP::Lite needs a re-write. SOAP::Lite needs to live up the "Lite" part of its name. SOAP::Lite should be built from the ground up to conform to the WS-i's requirements. It should be built first and foremost around a wicked WSDL parser and engine. It should be made more modular so that its components can be more easily swapped out for newer and better implementations without disrupting users and developers. It should take advantage of the number of perl modules that have evolved since SOAP::Lite was conceived to reduce code complexity and obscurity.

С поддержкой протокола XML-RPC, который также охватывается данной книгой, дела обстоят намного лучше. В Perl существует несколько реализаций и по крайней мере одна из них активно поддерживается и развивается.

Оценка по шкале ИМХО: 4

понедельник, 1 марта 2010 г.

Балдеющие от адреналина и зомбированные шаблонами

Балдеющие от адреналина и зомбированные шаблонами
Демарко, Листер, Хрущка, Макменамин, Робертсон, Робертсон

В этой книге авторы бестселлера Peopleware ярко и иронично рассказывают о том как вовремя осознать, что проект по разработке ПО движется в пропасть и он неминуемо потерпит крах если не предпринять срочных мер. Самое парадоксальное то, что большинство участников проекта и так прекрасно понимают когда дело идёт под откос, но по разным причинам предпочитают либо отмолчаться, либо создать видимость работы, либо приукрасить положение дел пока это ещё возможно. Так зачем же книга если всем и так всё понятно? Дело в том, что очевидные вещи доказывать сложнее всего, кроме того, есть целый ряд психологических и организационных барьеров, которые мешают трезво оценить ситуацию, признаться в том, что проблема действительно существует и найти пути выхода.

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

Оценка по шкале ИМХО: 5

понедельник, 22 февраля 2010 г.

Perl Testing: A Developer's Notebook

Perl Testing: A Developer's Notebook
chromatic, Ian Langworth

Эту книгу можно охарактеризовать как исчерпывающее руководство по тестированию на Perl без единой капли "воды". Тут есть всё: от примеров написания простейших тестов, до создания Mock-ов и тестирования баз данных. Как и другие книги из серии "A Developer's Notebook" издательства O'Reilly, эта книга организована по принципу "all lab, no lecture". Иначе говоря, "Perl Testing: A Developer's Notebook" - это аккуратный (подчеркиваю, аккуратный!) конспект по методикам тестирования на Perl. Каждый раздел (продолжая студентческую тему - каждый параграф) построен вокруг конкретного примера кода, решающего реальную задачу. Всё передельно лаконично и по делу. Вот как выглядит типичный раздел:

Тема раздела
Краткое введение и описание проблемы.

How do I do that?
Рабочий пример кода на Perl, решающий проблему.

What just happened?
Обсуждение ключевых моментов приведённого решения.

What about...
Небольшой FAQ вида "А что если мне нужно то же самое но чуть-чуть по-другому?"

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

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

Оценка по шкале ИМХО: 5

среда, 20 января 2010 г.

Perl Hacks

Perl Hacks
chromatic, Damian Conway, Curtis "Ovid" Poe

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

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

Ко второй части можно отнести полезные приёмы программирования, проектирования, отладки и тестирования. Тут же можно найти описание и примеры использования интересных Perl модулей, эффективные решения типовых задач.

Третью часть книги составляет откровенная экзотика - приёмы и технологии, которые могут потребоваться только для весьма специфичных задач.

В целом, видно, что почти за каждой статьёй стояла какая-то реальная задача для которой автор сумел найти яркое и поучительное решение. Часть материала пересекается с книгой Дамиана Конвея - Perl Best Practices. Вместе с тем, встречаются и статьи, мягко говоря, "высосанные из пальца". К примеру, в одном из советов предлагается использовать perl -wc для проверки успешности компиляции программы перед её запуском. Совет бесспорно дельный, но он скорее подходит для книги "Learning Perl", а не для "Perl Hacks". Возможно причина тому - издатель, который настоял на необходимом количестве рекомендаций: 101 и ни рекомендацией меньше!

В общем, "Perl Hacks" - увлекательное и полезное чтение для Perl-программиста практически любого уровня. Новички также могут почерпнуть в книге что-то полезное, но подавляющая часть материала всё-таки рассчитана на более опытную категорию программистов.

Оценка по шкале ИМХО: 5

воскресенье, 17 января 2010 г.

Запись и воспроизведение интерактивных shell-сессий

При работе в UNIX-среде часто возникает необходимость сохранить содержимое текущей shell-сессии для дальнейшего использования. К примеру, можно сохранить последовательность shell-команд в файл чтобы лихорадочно не вспоминать её когда она потребуется вновь. Этот файл может также послужить наброском для будущей статьи или какой-нибудь инструкции.

Самый очевидный способ - копирование всего ввода и вывода через буфер обмена. Хотя этот вариант и прост, он не особо удобен если данных очень много (чаще всего вывода). Отличная альтернатива - утилита script(1). Она запускает новую shell-сессию, весь ввод и вывод которой сохраняется в указанном файле (по умолчанию в текущей директории создаётся файл typescript):
script session.log
У программы script есть одна любопытная опция - -t Если она указана, то script выводит на STDERR временную информацию, иначе говоря, реальную скорость набора команд и получения их вывода. Имя под рукой содержимое shell-сессии и этот временной файл, сохранённую shell-сессию возможно "воспроизвести" подобно видеоролику (только консольному). Вот как это выглядит запись:
script session.log -t 2> session.time
А вот так можно воспроизвести сохранённый ролик (именно воспроизвести - сами команды, разумеется, заново не выполняются):
scriptreplay session.time session.log
Стоит отметить, что интерактивные программы, такие как top или mc также записываются и воспроизводятся без проблем. Однако есть один нюанс. Дело в том, что плеер не имеет понятия о том какого размера должно быть окно во время воспроизведения. Так, если сессия была записана на компьютере с 21-дюймовым монитором, причём окно псевдо-терминала было раскрыто на весь экран, то при воспроизведении на 19-м мониторе вывод таких интерактивных программ как top или mc исказится. То же произойдёт если во время записи менять размер окна псевдо-терминала. Другими словами, автоматически картинка не масштабируется.

В целом, запись и последующее воспроизведение shell-сессий вещь достаточно интересная, но область её применения довольно ограничена. Приведу одно из наиболее полезных применений для этой функции. Предположим вы хотите рассказать коллеге как выполнить ту или иную задачу. Объяснять это на словах не эффективно, а специально для этого писать статью - слишком долго. Как вариант, можно записать свой "мастер-класс" в виде консольного видеоролика и отдать его коллеге или коллегам для ознакомления.

В любом случае, даже если воспроизведение сессий не требуется, статическая запись всего ввода и вывода shell-сессий имеет массу полезных применений. Стоит отметить, что подобной функцией обладает и программа screen(1). Соответствующая команда называется C-a H.

Для записи и воспроизведения консольных роликов можно также попробовать пару программ ttyrec и ttyplay соответственно:
ttyrec tty.log
ttyplay tty.log
Программа ttyrec специально предназначена для записи интерактивных сессий. Временная информация и данные при этом сохраняются в одном файле.

Ссылки

понедельник, 11 января 2010 г.

Pipe Viewer - оценка скорости прохождения данных через pipe

При обработке очень больших файлов такими утилитами как tar, gzip, grep и др. порой возникает необходимость видеть ETA или по крайней мере скорость работы программы. Проблема в том, что большинство стандартных UNIX-утилит не отображает скорость обработки конкретного файла. В лучшем случае имеется ключ вида --verbose, при указании которого программа сообщает имя файла, который обрабатывается в настоящий момент. Ясно, что если файл очень большой и только один, то пользы от подобного ключа будет немного.

Однако, если программа умеет работать в режиме фильтра или по крайней мере читать данные со STDIN, то для оценки скорости её работы можно воспользоваться утилитой pv - Pipe Viewer. Она показывает скорость прохождения данных через pipe, а также ETA, если это возможно. Например:

pv very-big-file | gzip -c > very-big-file.gz
219MB 0:00:13 [16,3MB/s] [========> ] 34% ETA 0:00:24]

В данном примере pv действует аналогично утилите cat, считывая данные и передавая их дальше по конвейеру программе gzip. При этом, pv "знает" с какой скоростью gzip считывает входные данные со STDIN, размер файла также известен. Таким образом, можно достаточно точно получить ETA.

Ссылки