Home
Objective Caml
ocaml@conference.jabber.ru
Пятница, 10 июня 2011< ^ >
gds установил(а) тему: Камль -- http://caml.inria.fr | Логи -- http://chatlogs.jabber.ru/ocaml@conference.jabber.ru/ | Светлое будущее -- http://camlunity.ru/ | Нефильтрованное настоящее -- https://github.com/camlunity/kamlo_wiki | Портер прошлое -- http://gdsfh.dyndns.org/kamlo/ | Верблюды грязи не боятся! | release crap, enjoy NIH | репортьте баги официальным дилерам | ocaml мёртв, move on
Конфигурация комнаты
Участники комнаты

GMT+4
[00:29:06] Kakadu вышел(а) из комнаты
[00:49:43] gds вышел(а) из комнаты
[01:33:54] Typhon вышел(а) из комнаты: Replaced by new connection
[01:33:56] Typhon вошёл(а) в комнату
[01:44:57] zert вышел(а) из комнаты
[02:57:57] Typhon вышел(а) из комнаты
[03:50:43] ftrvxmtrx вышел(а) из комнаты
[03:51:45] ftrvxmtrx вошёл(а) в комнату
[05:47:03] komar вошёл(а) в комнату
[06:31:59] komar вышел(а) из комнаты: Replaced by new connection
[06:32:00] komar вошёл(а) в комнату
[09:06:44] gds вошёл(а) в комнату
[09:25:13] ftrvxmtrx вышел(а) из комнаты
[09:25:28] ftrvxmtrx вошёл(а) в комнату
[09:58:29] zert вошёл(а) в комнату
[10:29:19] komar вышел(а) из комнаты
[11:29:13] ftrvxmtrx вышел(а) из комнаты
[12:01:46] ermine вошёл(а) в комнату
[12:05:33] <gds> кстати, про итераты.  Сейчас проектирую такую штуку: результат запроса к БД будет обрабатываться итератом, внутри которого будут вложенные аппликативные функторы (1).  Представьте себе, самое кошерное решение из тех, которые можно позволить себе в относительно-общем dbi без статических проверок, но и без явных недостатков (без концептуальных -- то есть, можно оптимизировать всё до весьма прилично-мелкого оверхеда, хоть первая реализация будет неоптимальна, но прилична).
Про (1) вскоре напишу в жыжыцу, там клёво.
[12:12:39] ftrvxmtrx вошёл(а) в комнату
[12:15:25] <ermine> gds: я так и не поняла - у тебя sql - это DSL сам по себе или набор буковок :)
[12:20:21] <gds> ermine: перлячье-петонье dbi видела?  пока у меня примерно так.  и пока исполняется только чистый sql в виде строк с пейс-холдерами.  ибо это -- нижний уровень, по универсальности и гибкости самый крутой, а остальное вполне делается поверх него.
например, можно сделать embedded dsl на тех же итератах в будущем -- например, итерат "drop 10 >>= fun () -> joinI (take 20 & fun record -> expr)" обрабатывать не тупо, а частично выносить из него в sql -- например, в этом примере можно заменить "исходный-sql-запрос" на "select * from (исходный-sql-запрос) offset 10 limit 20".
[12:29:09] <gds> а, ещё прикол с итератами.  Их recoverable errors позволяют сделать такой финт ушами: если есть какой-то код, берущий данные записей в виде окамловских значений (например, завёрнутые в sql_t = String of string | Number of int), и если захотим пропустить стопиццот записей, не преобразовывая каждое их значение в sql_t, то пишем итерат drop, который внутри себя будет кидать recoverable error: exception Drop_records of int, и которую енумерат словит обработает так: пропустит данные записи, не преобразовывая их в sql_t, а остальные записи даст тому продолжению, которое передаст новый-модный drop (то есть, то, к чему его прибиндят).  Прозрачно, красиво.
[12:31:45] <ermine> gds: а если dba поменяет чонить в структуре?
[12:32:12] <ermine> будешь искать по всему коду, где сломалось, и править?
[12:32:39] <ermine> сдается мне, что в ходе поправок найдутся еще две никем не замеченные ранее баги
[12:34:24] <gds> универсального/идеального решения тут нет, поэтому нужно реализовать максимально простое решение, хотя бы не усложняющее разборки.
И, вероятно, надо будет написать "расслабленные" комбинаторы для типизации значений, позволяющие попытаться взять int там, где в базе varchar2, с преобразованием в int, если получается (и с фейлом там, где не вышло).
[12:36:40] <gds> и да, если формально проверить у меня нет возможности, coding guide только и помогут -- держать весь доступ к БД в одном модуле, например.  А то и вообще, запросы в отдельных файлах.  Но пока не знаю.
[12:36:50] <ermine> с постгресом это не пройдет
[12:37:12] <gds> что именно?
[12:37:24] <ermine> varchar -> int
[12:37:49] <ermine> ну постгрес таки типизируется более-менее, за исключением шняги с NULL
[12:38:39] <gds> пройдёт всё -- как изменение типа столбца (пусть через добавление промежуточного), так и попытка применить int_of_string на результат.
[12:39:42] <ermine> ну вот - dba поменял тип столбца, и что станет с твоей прогаммулькой?
[12:40:06] <gds> смотря как поменял и смотря как поменялись данные.
[12:40:14] <ermine> опять искать по всему коду и добавлять то ли ::int, то ли еще какие свистопляски устраивать
[12:40:41] <ermine> мне бы больше понравилось проверка вменяемости кода на этапе запуска/компиляции
[12:40:43] <gds> универсального решения нет по-любому, если не хочешь "компилироваться супротив созданной схемы данных" (а я вот не хочу).
[12:42:03] <ermine> ну вот сначала же практиковался такой метод - на этапе запуска проги сами создавали таблицы и сравнивали то что было, потом позднее добавилась проверка на этапе компиляции
[12:42:07] <gds> типы -- это ещё мелочи, бывают другие изменения.  например, раньше было ограничение уникальности, а теперь внезапно не стало его.  если клиентский код полагался на это ограничение, проверяемое базой, то он поломается.  вообще, слишком много надо проверять.  чисто типы столбцов -- это частичное решение проблемы, а полного я не вижу.
[12:42:52] <ermine> бугзилла, redmine и прочие крутые багтрекеры успешно апдейтят базы под новые версии
[12:43:32] <ermine> вот бы мне вменяемую апдейтилку
[12:44:29] <gds> апдейтить автоматически можно только в случае простых изменений.  Опять же, частичное решение -- феее.
[12:45:20] <ermine> да ладно
[12:45:37] <ermine> универсального парсера тоже нет, и ничо, жрут кактус
[12:45:37] <gds> ладно, да.
[12:46:08] <ermine> я вот тут задумалась о том, что такое инпут
[12:46:38] <gds> с парсерами история хитрее -- обычно их хватает, чтобы парсить всё разумное.  А вот изменения схем зачастую настолько хитры, что средняя апдейтилка только 80% случаев обработает.  Нафиг надо.
[12:47:27] <ermine> то ли окамлевый stream (берешь одно за другим), то ли строка, по которой надо бегать в обе стороны, то ли чота еще, и пыталась представить себе инпут не в виде строки или стрима
[12:47:44] <ermine> инпут в виде числа как-то слабым показался
[12:48:13] Typhon вошёл(а) в комнату
[12:50:09] <ermine> у числа вот нет EOF, и это видимо его уникальная особенность
[12:50:56] <gds> не понял, как это?
[12:51:13] <ermine> а есть?
[12:51:38] <gds> не понимаю, аб чом речь.
[12:51:42] <ermine> последовательность чисел завершается EOFом, я тут не спорю
[12:52:29] <ermine> gds: ну определение input как таковой сущности, получается, что это может быть только последовательность чего-то
[12:53:02] <ermine> gds: а инпут не в виде последовательности бывает такой, чтобы его можно было пилить парсерами и итератами?
[12:54:14] <gds> я бы только так и рассматривал -- идущие по порядку элементы, количеством от 0 и выше, для простоты -- одного типа.
а зачем пилить инпут, который не последовательность?  Ну, в частном случае, из любого значения можно создать последовательность из 1 элемента, содержащего это значение.
[12:54:29] <ermine> gds: число можно разбирать по-всякому (вертикальные итараты)
[12:54:56] <gds> но зачем разбирать число по-разному?  число оно и есть число.  или недопонимаю?
[12:55:17] <ermine> делить на два и на три
[12:55:24] <ermine> например число 6
[12:55:36] <ermine> ну поиск множителей чоли
[12:55:43] <gds> возьми да подели, есть арифметические операции, нафига тут парсеры?
[12:56:49] <ermine> gds: ну дело не в арифметике, а в том, что такое инпут
[12:56:55] <gds> что на входе и что хочется на выходе?
[12:58:01] <ermine> gds: переформулирую еще раз! бывает ли инпут для итератов не из последовательности?
[12:59:46] ftrvxmtrx вышел(а) из комнаты
[12:59:49] komar вошёл(а) в комнату
[12:59:49] <gds> инпут -- в смысле, хочется дать итерату просто одно значение?  можно сделать последовательность, содержащую его.
можно ли сгенерировать из одного значения последовательность по определённым правилам и накормить ею итерат? -- можно.
[13:00:17] ftrvxmtrx вошёл(а) в комнату
[13:02:02] <ermine> ых
[13:02:09] <ermine> всё сводится к последовательности
[13:05:03] gds away на часик
[13:05:41] gds вышел(а) из комнаты
[13:11:01] Kakadu вошёл(а) в комнату
[13:57:34] gds вошёл(а) в комнату
[14:00:37] <gds> ermine: впрочем, мне для дби пригодился бы трюк "подсовывать range set в качестве входа, получать значения функцией int -> 'a".  но это как бы тоже последовательность, только в сжатом виде.
[14:04:33] <ermine> gds: генератор последовательности?
[14:04:45] <ermine> ну это не интересно
[14:05:32] <gds> не интересно, зато нужно лично мне для лично моих целей.  и не просто последовательность.
[14:06:34] <ermine> не интересно в том смысле, что инпут с последовательностью - это и есть генератор последовательности
[14:08:14] <gds> а, это да.
[14:09:09] <ermine> gds: вот для полного идеалу бы мне еще понять как генератор последовательности уживается с бэктрейсами
[14:10:19] <gds> ermine: а тебе точно нужны бэктрейсы и точно не хватит "параллельный парсинг альтернатив"?  или чего-то недопонимаю?
[14:10:54] <ermine> gds: с левой факторизацией?
[14:11:28] <ermine> gds: я как-то слабо владею методами удаления бэктрейсов, особенно автоматическим построением левой факторизации
[14:11:32] <gds> чото я уже забыл всю эту байду с факторизациями, давно занимался.
[14:12:38] <ermine> gds: ну левая факторизация - ветвление с общим листом например по знакам арифметики, а не по слагаемым
[14:12:48] <f[x]> s/бэктрейсы/бэктрэкинг/
[14:13:19] <gds> о да, моск перешёл в режим экономии :[
[14:13:31] <ermine> бэктрейс бывает не только по входным данным, но и по коду, как в том ужасном delimcc
[14:14:28] <gds> я бы посмотрел, как в парсерах а-ля glr делается арифметика и сколько они при этом жрут.  вроде это просто найти.
[14:16:58] <ermine> а есть ли бэктрейсв в конечных автоматах?
[14:17:26] <ermine> у них-то как раз зверская факторизация, по-моему
[14:20:05] abiogenesis вошёл(а) в комнату
[14:20:55] abiogenesis вышел(а) из комнаты
[14:24:56] ermine ищет в гугле арифметику в glt
[14:25:44] <gds> ermine: лучше в "glr"
[14:26:59] <ermine> gds: точно :)
[14:27:47] <ermine> http://www.haskell.org/happy/doc/html/sec-glr-semantics.html
[14:27:51] <ermine> забавно
[14:29:11] <ermine> но нифига не понятно
[14:29:50] <ermine> у Киселева в талмуде про итераты, кстати, проскакивала мысль, что его итератц рулят, потому что не вытащат ничего лишнего из инпута
[14:30:06] <ermine> вообще мрак
[14:32:55] <gds> да, не вытащат ничего лишнего, а всё, что вытащат, постараются максимально полно обработать.
[14:34:35] <ermine> gds: у него там конец строки в трех вариантах, я так поняла, что по киселеву конец строки - это \r или \n одиночный символ, т.е. если дальше идут  \n или \r, то ему пофиг, пусть это у него будет просто новая строка
[14:34:46] <ermine> на следующем шаге итерата
[14:35:09] <ermine> это фальш, за уши притянутая к конкретной задаче
[14:35:38] <gds> у него конец строки -- \r, \r\n либо \n.  Вроде в rfc2616 похожее определение.
[14:36:30] <ermine> gds: не, у него три варианта именно (а не в рфц)
[14:36:42] <gds> а чем неправильно?
[14:37:35] <ermine> gds: ну, а если мне нужна настоящая пустая строка?
[14:38:23] <ermine> киселев допускает наличие LFCR
[14:38:45] <ermine> тут никакой настоящей пустой строки не выйдет без погляда вперед
[14:38:59] <gds> тебе как генерирующей стороне?  \n\n | \r\r | \r\n\r\n | \r\n\n | \r\n\r | \n\r, может какой-то ещё вариант упустил.
[14:40:34] <ermine> gds: ну вот \n\r - это наличие пустой строки или нет (по киселеву) - это еще вопрос :)
[14:40:57] <gds> сейчас открою код и дам ответ.
[14:41:09] <ermine> лично у меня определение конца строки проще \r?\n, а все остальное пусть лесом идет
[14:41:29] <ermine> хтя в винде странные концы строк
[14:44:10] <gds>   let terminators =
    heads crlf >>= fun n ->
    if n == 0
    then heads lf
    else return n
этот итерат возвращает 0 в случае, если конец строки не найден.  В первой строке тела он пытается заматчить ['\r'; '\n'] и возвращает, сколько заматчено.  Если не 0, то это значение возвращает.  Если 0, то возвращает, сколько символов из списка ['\n'] заматчено.
[14:45:01] <gds> хочешь -- сделай \r?\n, достаточно будет слегка поправить кодэ.
[14:46:31] <gds> точнее, не слегка, и лучше вообще чуть по-другому написать, покрасивше.
[14:46:33] <ermine> это ведь твой код
[14:46:52] <gds> да, мой, но я спортил олеговский код напрямую тут.
[14:47:28] <ermine> а там у него break еще был до терминаторов
[14:48:07] <gds> ermine: http://paste.in.ua/2570/
[14:49:49] <ermine> а чо там за & ?
[14:49:59] <ermine> х-ло-перлизация?
[14:50:31] ermine уже смирилась с >>. >>=, ||| и с трудом воспринимает дополнительные значки
[14:51:00] <gds> value ( & ) f x = f x;
[14:51:31] <gds> а для io-манатки там вообще рыбьи скелеты!  >>% и %<<
[14:53:38] <ermine> gds:  return & ((if ts = 0 then `No_term else `Term), l) а для чего тут & ?
[14:54:03] <gds> раньше было что-то другое, видать.  конкретно тут -- не нужен.
[14:54:54] <ermine> gds: сорри, что придралась :)
[14:55:36] <gds> ничо-ничо, лучше так, чем недопонимать какую-нибудь хрень.
[14:56:35] <ermine> да погоня за х-лем не всегда к добру приводит
[14:56:55] <ermine> еще неизвестно, нужны ли монады на самом деле в камле
[14:57:28] <gds> а я и не гнался.  мне итераты нужны были, вот и всё.
монады -- полезная концепция, лично мне они нужны (не везде, понятное дело).
[14:59:09] <gds> вон, на сишечьке итераты делал народ, так вроде ничо, сишники отреагировали нормально.
[15:00:24] <gds> (те, кто хоть что-то понял, разумеется.)
[15:04:35] <ermine> в цэ же нет карринга
[15:05:54] <gds> это можно эмулировать, в теории.  на практике же -- недостаточно смотрел в тот код.  у меня вообще не слишком крепкие нервы.
[15:06:18] <ermine> а вообще код твой в пасте не по-детски сложный
[15:06:54] <ermine> gds: эмулируют записью в структуры указателями на функции
[15:11:43] <ermine> почитаю еще итераты степ бай степ, хотя там ужасно многа букфф
[15:15:59] <gds> ermine: код пасты -- если бы писал сейчас, то всего лишь не выносил бы check в отдельную функцию.  было бы понятнее, как-то типа:
break_chars (fun c -> c == '\r' || c == '\n') >>= fun l ->
let () = dbg "http_line: %S\n" l in
terminators >>= fun ts ->
return ((if ts = 0 then `No_term else `Term), l)
куда дальше упрощать -- не знаю.  заинлайнить terminators разве что :)  ну так тривиально делается.
[15:16:36] <ermine> gds: еще можно посчитать, сколько аллокаций создается в результате выполнения кода в пасте
[15:20:22] <gds> ermine: от большинства можно легко избавиться, будь на то нужда (если профайлер покажет).  Фактически, итерат на вход получает массив символов -- ведь несложно найти строку в этом массиве и пропустить конец строки.  Ну и вернуть результат вида IE_done/IE_cont.  Я насчитал три аллокации максимум (строка результата + остаток строки + значение "IE_done результат остаток").
[15:23:24] <ermine> gds: я пока не поняла, почему ты зациклился на массивах
[15:23:36] <ermine> у тебя там же функтор?
[15:23:49] <ermine> а не пофиг ли как выглядит последовательность?
[15:24:22] <gds> функтор у меня там только над IO.  Над контейнером я функтора не делал.
Не пофиг, потому что разные последовательности обладают разными характеристиками доступа к ним.
[15:25:07] <gds> могу разве что сделать там вариант Subarray vs Substring и заворачивать символы в строки -- это скорее всего надо будет.  А остальное -- даже не знаю.  Надо думать.
[15:25:14] <gds> (над подстроками я уже подумал.)
[15:26:44] <ermine> gds: я для себя определила, что любая последовательность имеет проперть итерации, поэтому пофиг, в чем сущность последовательность, надо только определить эту проперть, кстати, из-за него немного помучилась с функторизацией тут недавно
[15:27:26] <gds> итерация = один вызов на каждое взятие следующего элемента?
[15:27:36] <ermine> теперь думаю - не объединить ли эти два фукнтора в один
[15:29:01] <gds> когда мне будет надо запустить параллельно два итерата на одних и тех же данных, я просто подсуну им одинаковые подмассивы.  Тебе же придётся делать Stream.dup (посмотри в батарейках, весёлый код).
[15:29:01] <ermine> хз, или подсовывание каждого следуюшего элемента в вызов функции
[15:30:00] <ermine> мне придется склонировать инпут скорее всего
[15:30:21] <ermine> без копирования
[15:30:42] <ermine> чтобы в каждом итерате были свои указатели
[15:31:02] <ermine> но они похоже не особо нужны будут, если найду как без бэктрейсов жить
[15:31:07] <gds> представим, что один парсер у тебя скушал 10Мб данных, а второму что-то не нравится, он ждёт.  Получается, эти 10Мб будут висеть в памяти, на случай, когда второй парсер одумается?
[15:31:46] <ermine> если бы инпут был списком, то наверное указатели как раз не нужны
[15:33:20] <ermine> gds: было бы проще, если бы понять практическую ценность вертикальных итератов
[15:33:36] <ermine> а так - ничо, кроме счетчика трафика, не придумывается
[15:36:05] <ermine> можно другой пример - распознаватель протоколов
[15:36:34] <ermine> тут все итераты, кроме одного, должны умереть палюбому
[15:37:27] <gds> подмассивы/подстроки в среднем будут быстрее, так как функции, обрабатывающие их, обычно весьма "big-step" -- например, "выкинуть всё до символа x", и эти функции знают конкретную структуру, лежащую снизу -- например, могут обращаться к строке через String.get_unsafe.
[15:38:34] <gds> вертикальные итераты -- например, фрейминг take у олега, ограничение итерата конкретным числом элементов limit у меня, или мой utf8 : enumeratee char uchar 'a.
[15:39:43] <gds> распознаватель протоколов -- вполне грамотное применение, можно и без вертикальных тут, просто комбинатор над несколькими итератами, а вертикальные скорее для преобразования одного потока в другой поток.
[15:40:56] <ermine> gds: окей, для видео сгодинся, в мире вэба принято енкодить в три формата
[15:41:08] <gds> кстати, в какие?
[15:41:11] <ermine> только вот проц выдержит ли
[15:41:42] <ermine> в theora, h.268, еще одна theora/ogg
[15:42:05] <ermine> у теоры еще комбинации по формату звука вроде
[15:43:33] <gds> ermine: http://paste.in.ua/2571/
[15:44:31] <gds> и как только останется один итерат, функция его возвращает, и дальнейшая работа ведётся исключительно с ним, itlist_anyresult_lasterror  уже не причём, уже не работает передастом чанков.
[15:47:41] <gds> а хотя нет, кое-что по-другому там.  Но довести до описанного поведения несложно.
[15:48:19] <gds> достаточно в строке
`Cont lst -> ie_contM & step lst
смотреть, если остался только один итерат в lst, то возвращать его, пусть его напрямую кормят.
[15:49:56] <ermine> о, там where, еще один признак идолопоклонства!
[15:50:44] <ermine> на первый взгляд кажется, что там итераты сначала тестируются, не схлопнулись ли они, и потом решается, что с ними делать
[15:50:54] <ermine> да?
[15:51:10] <ermine> это в последней функции
[15:52:48] <ermine> с семантикой вообще напряг
[15:53:17] <gds> ermine: именно так.  Ключевой момент таков: если остался список, то частично-применённая step lst будет хотеть ещё данные, которые распихает куда надо.
[15:54:18] <gds> where -- ну бывает, что реально удобнее читать сверху вниз, особенно в случаях, когда сверху (до where) написана тривиальщина, как часто бывает в итератах.
[15:54:31] <gds> с какой семантикой напряг?
[16:11:16] <gds> ermine: таки откошерировал:
| `Cont [] -> assert False
| `Cont [it :: []] ->  IO.return (it, empty_stream)
| `Cont lst -> ie_contM & step lst
вторая строка как бы говорит нам: "из итерата возвратим продолжение, такое, что следующие данные будет принимать итерат it, а остатка потока никакого нет, так как скушали всё".
[16:28:45] klapaucius вышел(а) из комнаты
[16:33:29] <f[x]> от запуска make до начала вычитки setup.data - полсекунды
[16:33:34] <f[x]> оазис = тормоза
[16:36:01] <f[x]> а потом ещё секунду ocamlbuild шарится по каталогам с тестовыми файлами - facepalm
[16:36:12] <f[x]> кстати на .git тоже рекмоендуется -traverse делать
[16:40:33] <ermine> а не -include?
[16:42:08] <ermine> gds: насчет семантики - First_result, Last_result, Cont
[16:42:21] <ermine> чота не припомню, чтобы Киселев фантазировал на эту тему
[16:42:38] <gds> а что не так?
да, у киселёва этого не было.
[16:43:22] <ermine> ну, зачем вообще начало и конец и середина?
[16:43:35] <ermine> конец и середина - ладно, а начало зачем?
[16:44:23] <ermine> ой, там last_error
[16:44:55] <ermine> ну, еще загадочнее стало
[16:45:46] <ermine> может лучше переименовть в Fatal_error, он-то точно Last :)
[16:46:33] <gds> там мне нужно было такое: взять первый/любой результат, а в случае отсутствия -- вернуть последнюю из ошибок.  этот код разбил на две функции (декомпозиция), и поименовал эти варианты.  а как бы ты стала решать подобную задачу -- не разбивала бы на функции?
[16:48:50] <ermine> gds: я пока задачу толком не видела, потому что не представляю себе, что результат может быть первым/любым
[16:49:43] <gds> ну вот, мне нужно было именно "первый результат либо последнюю ошибку", и в названии функции, и в промежуточных вариантах я как раз это описал.  Как-то так.
[16:50:15] <ermine> результат или есть, или его нет, а у итерации нет начала, даже у фолда тоже нет, поэтому ему дают костыль в виде начального значения
[16:51:58] <ermine> gds: ну если это из-за того, что в state не удалось запихнуть - что-то в концепции хромает
[16:52:48] <ermine> если я прально не поняла, то первый результат - это, например, значение из хидера Host: ..., который потом суется куда попало
[16:53:09] <ermine> или версия протокола, что еще лучше
[16:53:43] <ermine> монады - зло
[16:53:44] <gds> это (`First_result | `Cont | `Last_error) удалось бы запихнуть в состояние, но я провёл декомпозицию функции.
про "нет начала" -- это ты про что?
[16:54:24] <ermine> gds: не-не
[16:54:59] <ermine> в состояние только то, что полезного выдралось из инпута, и эти полезности нужны для работы сделующих шагов, не так ли?
[16:55:40] <ermine> gds: ну я же не знаю, нафига тебе вдруг понадобился именно первый/любой результат
[16:56:03] <gds> в состоянии у меня находится только список итератов, которым нужны ещё данные.  У каждого из них есть какое-то своё состояние, но мне это не важно совершенно.
[16:57:05] <ermine> дальше
[17:09:36] <gds> ermine: если бы я разбирал http 1.0 vs 1.1, я бы наверное разобрал первую строку явно, вернув версию, а потом по версии бы смотрел.  А вот явно разнородные протоколы, конечно, проще разбирать "альтернативой" двух итератов.
[17:22:59] Digimmortal вошёл(а) в комнату
[17:30:21] <ermine> gds: тогда я так понимаю, что First_result - это результат первого итератора из списка вертикальных итератов?
[17:30:43] Kakadu вышел(а) из комнаты
[17:31:15] <ermine> я бы всё завернула в unit и спала бы спокойно
[17:35:11] <gds> ermine: тут вертикальных (enumeratee) нет, тут типа комбинатора что-то.  First_result с результатом возвращает вспомогательная функция, которая кормит все итераты тем чанком, который ей дают (она тоже итерат, тоже имеет право на чанки).  Если кто-то из свежепокормленных итератов возвратил результат (т.е. дошёл до состояния IE_done), вспомогательная функция возвращает этот результат в First_result, и основная функция (основной итерат) возвращает этот результат в качестве своего результата.
[17:46:55] <ermine> gds: понятно, хотя ничего не понятно
[17:49:42] <gds> ermine: кто-то кормит итерат чанками.  представим, что есть несколько итератов.  рисуем же такой итерат, который кормят чанками, и который передаёт эти чанки "детям".  вот и всё.
[17:53:30] <ermine> gds: это наверное накладки в имплементации!
[17:53:41] <ermine> я еще коды буду разбирать как-нить
[18:54:46] Kakadu вошёл(а) в комнату
[19:52:34] ftrvxmtrx вышел(а) из комнаты
[21:02:53] Typhon вышел(а) из комнаты
[21:15:57] ftrvxmtrx вошёл(а) в комнату
[21:19:26] Digimmortal вышел(а) из комнаты
[21:24:16] fegdri вошёл(а) в комнату
[21:28:36] fegdri вышел(а) из комнаты
[21:28:49] fegdri вошёл(а) в комнату
[21:29:15] fegdri вышел(а) из комнаты
[21:54:30] fegdri вошёл(а) в комнату
[21:54:42] fegdri вышел(а) из комнаты
[21:54:52] fegdri вошёл(а) в комнату
[21:54:59] fegdri вышел(а) из комнаты
[23:12:04] komar вышел(а) из комнаты
[23:12:20] komar вошёл(а) в комнату
Powered by ejabberd Powered by Erlang Valid XHTML 1.0 Transitional Valid CSS!