суббота, 16 апреля 2011 г.

Прочитал вчера вот эту статью: http://easy-coding.blogspot.com/2011/04/go.html
Итак: данная программа берет TAR с исходниками, распаковывает его, и каждый файл прогоняет через компилятор. Сразу скажу, цель того, что я все это пишу тут, это продемонстрировать (и не более того), как просто и удобно на Go можно писать многопоточные императивные программы.
и не впечатлился. Эта программа реализует простую вещь - Master/Worker pattern. Каких-либо особых преимуществ языка Go в этом нелегком деле я не заметил. Для написания этой программы, язык программирования вообще не важен, он должен позволять запускать потоки и использовать блокирующие очереди, вот и все. Все тоже самое может быть написано на C++, с использованием класса tbb::concurrent_queue, или на C#, с использованием класса BlockingCollection. Код будет выглядеть так же просто.
Мало того, на шарпе, можно написать как-то так:

using(var tar = new TarReader(tarname)) 
{
    var files = tar.NewReader(tmpdir);
    Parallel.ForEach(files, file => Compiler.Run(file, params));
}

(далее, имена всех классов и методов вымышлены, все совпадения - случайны)
 Допустим, tar - объект, читающий tar архив, метод NewReader(tmpdir) - возвращает IEnumerable, при обходе которого на диске, в каталоге tmpdir, будут создаваться новые файлы, а итератор будет возвращать их имена. При вызове tar.Dispose() - все временные файлы должны быть удалены.
Допустим, у нас есть класс Compiler, со статическим методом Run, который получает имя файла и набор флагов, в виде строк, запускает компилятор, дожидается когда он отработает и завершает работу.
Вот собственно и все. TPL не будет создавать 100500 потоков, количество выполняемых параллельно задач будет зависеть от количества процессоров. Возиться с очередями и балансировкой нагрузки - не нужно. Обработка ошибок - проще некуда.
Возникает логичный вопрос - зачем этот Go вообще нужен? :)