пятница, Январь 30, 2009

The validation problem

Сложно найти программиста, который бы никогда не сталкивался с задачей проверки пользовательских данных. Буквально на первой же лабе в институте, преподаватель "ломает" программу некорректным вводом. Почти все через это прошли и признают, что относится к входным данным нужно со здоровой паранойей. Вопрос лишь в том, где именно проверять входные данные. Возбужденные сторонники ООП поднимают на щит инкапсуляцию и провозглашают немедленную валидацию на уровне классов бизнес-сущностей, бородатые DBA ратуют за проверки на уровне БД, очкастые архитекторы стоят на вынесении валидаторов в отдельную сущность, аппелируя к SRP. Разумеется, все они правы по-своему.

Есть такая штука, которая называется инвариантом системы. Это такой набор утверждений, истинных в любом ее состоянии. Хороший пример такого инварианта -- бухгалтерский баланс. Сумма активов равна сумме пассивов. Если это не так, значит где-то произошла серьезная ошибка. Для отдельных компонентов могут быть свои инварианты, попроще. Например, для любого счета всегда известна валюта или метод никогда не возвращает null. В первую очередь инварианты нужны внутри самой системы. Если мы знаем, что для всех счетов всегда известна валюта, мы можем обращаться к ней без проверки не рискуя получить NullPointerException. Кто же ответсвенен за консистентное состояние системы? Очевидно, сама система. Технически это можно сделать разными способами. Годятся простые проверки, вынос обязательных полей в конструкторы, констрейнты на базе, ассерты, современные средства контрактного программирования и все прочее, что придет в голову. Однако у инварианта есть side effect в том, что каждое дополнительное утверждение снижает гибкость системы. Если какое-то состояние системы нарушает инвариант, оно невозможно, независимо от желаний программиста. Избыточность в инварианте системы приводит к тому, что вместо простых действий устраиваются танцы вприсядку с целью обойти инвариант.

Чтобы избежать этой опасности, инвариант следует тщательно оберегать от распухания. Для того утверждения не влияющие на целостность системы целесообразно выделить в отдельный слой. Например, в системе никому не требуется номер паспорта клиента, но с точки зрения бизнеса это поле относится к обязательным, потому что по закону положено. Более того, часто возникают ситуации, когда в одних случаях поле является обязательным, а в других опциональным. Например, паспортные данные требуется от клиента клиент собирается получить деньги и небязательны если он принес деньги отдать.

Проверки, которые не входят в инвариант стоит собирать в одном месте, что значительно упрощает внесение изменений. Тут хорошо годятся и отдельные классы *Validator, валидаторы на основе XML правил и т.п. Если правила меняются неприлично часто, хорошо помогает вообще отдать настройку правил валидации админу. Пусть он в рантайме поднимает галочки. Пользователи будут довольны.

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

воскресенье, Январь 11, 2009

Chinese classification

Среди людей занимающихся семантикой распространен мем "китайская классификация" -- таксономия с "плавающим" основанием. Корни этого термина растут из эссе Борхеса "Аналитический язык Джона Уилкинса" в котором он упоминает некую китайскую энциклопедию под названием "Небесная империя благодетельных знаний". На ее древних страницах написано, что животные делятся на:

  1. принадлежащих императору;
  2. бальзамированных;
  3. домашних;
  4. молочных поросят;
  5. сирен;
  6. сказочных;
  7. бродячих псов;
  8. включённых в эту классификацию;
  9. бешеных;
  10. бессчетных;
  11. нарисованных тончайшей кистью из верблюжьей шерсти;
  12. прочих;
  13. только что разбивших кувшин;
  14. издалека кажущихся мухами.

С точки зрения современного образованного человека китайская классификация выглядит дико. С другой стороны такие классификации встречаются повсеместно, достаточной вспомнить классификатор жанров FB2, библиотечный каталог, или классификатор МКБ-10. ailev вообще высказал мысль о том, что все онтологии -- это замаскированные китайские классификации, ибо именно таковые классификации лежат в основе мира, именно к таким классификациям привыкли люди. Если это так, возникает вопрос, откуда берутся "китайские классификации" и почему люди охотнее создают и пользуются ими вместо строгих таксономий?

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

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

пятница, Декабрь 19, 2008

Data about data

Если открыть спецификацию какого-нибудь формата данных, в ней скорее всего обнаружится раздей посвященный метаданным. Иногда, такой раздел превышает остальную спецификацию в несколько раз по объему и по сложности. В то же время, на практике метаданные используют весьма и весьма нечасто. Существуют даже форматы, которые никто так полностью и не имплементировал, по причине невостребованности. Например, тот же ID3v2 (метаданные для MP3) с его несколькими сотнями тегов начиная от автора песни и заканчивая переводами лирики. Или EXIF, которым пользуются ровно потому, что все современные камры пишут в него параметры съемки. Еще ни разу не видел, чтобы из него кто-нибудь использовал разделы описания или копирайта. Или FB2, по поводу метаданных которого регулярно возникают споры на форумах о том, как их заполнять. Или MARC, с правильным заполнением которого проблемы даже у профессиональных библиотекарей, хотя им-то сам бог велел прекрасно разбираться в предметной области. И какой формат ни возьми, с метаданными будет плохо. Или мало, или много, или в самый раз, но совсем не то, что нужно.

Для того чтобы понять почему так происходит, нужно определить, что такое метаданные. Лаконичное определение из заголовка, конечно, прекрасно, но оно ничего не говорит о том, какие это данные. Почти все факты о данных можно представить в виде утверждений <субъект, свойство, значение>. А набор свойств из предметной области и доменов для значений суть онтология. Например, фокусное расстояние это свойство, которое может принимать значение типа длина (а не угол или скорость). В большинстве форматов онтология жестко зафиксирована, так что не бросается в глаза, но она всегда присутствует.

Вернемся к проблеме. Разработчик формата всегда держит в голове какой-то способ использования этого формата. Иначе он в принципе не смог бы разработать ничего полезного. Однако, как только он фиксируеется на способе он начинает представлять себе предметную область с одной, узкой, точки зрения. В результате получается онтология, описывающая каую-то узкую область, которую разработчик считает верной. Однако, у пользователей совсем другое мнение на этот счет. Почти наверняка кто-то будет использовать формат по другому. ID3 созвался для музыки, но его можно использовать для кучи разных вещей: от записи телефонных разговоров, до калибровочных сигналов дефект-детекторов. EXIF хорошо описывает метаданные съемки, но не годится для описания преобразований, проделанных с оригинальным изображением. Проблема в том, что невоможно предусмотреть все способы использования метаданных и разработать всеобъемлющую онтологию. Более того, такие попытки почти всегда приводят либо к излишней общности либо к излишней сложности. И то и другое отталкивает пользователей от использования метаданных. Хуже, когда появляются несколько стандартов метаданных для одного формата. В итоге каждый софт какие-то форматы метаданных поддерживает, а какие-то нет, что еще сильнее отвращает пользователей. Никому не хочется описывать файл, если при следующей обработке или конвертации эти сведения потеряются.

Как можно с этой проблемой справиться? Если вы разработчик формата, не пытайтесь думать за пользователей -- все равно не выйдет. Дайте им возможность определять собственные онтологии и снабдите их парой убедительных примеров для конкретных узких областей. Хороший пример движения в нужном направлении Adobe XMP основанный на RDF. Нельзя сказать, что этот формат идеален, но хоть что-то.

пятница, Ноябрь 28, 2008

Time to live

У каждого предмета есть определенное время жизни. Рано или поздно он устареет, износится и потребует замены новым. Или просто исчезнет проблема, ради решения которой этот предмет создавался, как исчезли мундштуки, подстаканники, пресс-папье и буфеты. Это касается не только материальных объектов, но и информации, в том числе и информационных систем. У каждой строчки кода, у каждого килобайта данных есть собственное время жизни. Время жизни есть даже у таких неосязаемых сущностей, как идеи или соглашения. Для того, чтобы научиться оценивать характерное время жизни, нужно хорошо понимать механизмы разрушения объектов. Например, автомобиль может разрушится в результате аварии, физического износа или морального устаревания. Если известно, что автомобиль морально устареет через 10 лет, нецелесообразно обеспечивать его надежную работу в течение большего срока. Все равно к тому времени он уже окажется под прессом. Знание характерного времени жизни позволяет поддерживать качество на необходимом уровне, не больше и не меньше. Зачем делать автомобиль надежным, если через 10 лет он все равно окажется на помойке, где не важно работает он или нет.

Данные

Оставим за скобками временные данные, которые на то и временные, что их время жизни невелико. Для данных постоянных время жизни составляет от 25 лет до бесконечности. Данные редко становятся не нужны, a накопленные за долгие годы данные невозможно ничем заменить. Например снимки допоптопных аппаратов советской серии Венера, несмотря на отвратительное качество будут жить еще долго. Сперва в качестве основного источника информации, затем для сравнения с современными снимками и анализа изменений. Обычно, вменяемые люди стараются не уничтожать данные, мало ли что еще пригодится. Вдруг завтра из них удастся извлечь новую информацию. Мне доводилось работать с базами, которые пережили три поколения бизнес-кода и переживут еще как минимум столько же. Поэтому к проектированию баз данных нужно относиться особо внимально. Любое ваше сиюминутное решение в угоду производительности или простоте кодирования будут с матюками вспоминать через много лет. Изменить что-то в унаследованной базе, в которой уже накопились гигабайты данных нереально сложно.

Протоколы и стандарты

Две причины, по которым устаревают стандарты и протоколы: они перестают отвечать изменившимся требованиям или появляется способ сделать то же самое проще. Поскольку технологии непрерывно меняются и то, что раньше требовало дестятка PhD, сегодня доступно школьнику, редкий стандарт проживет больше 10 -- 15 лет. Затем, если представится возможность, он отправится на помойку истории. К сожалению это происходит не всегда. Очень часто изменения уже внедренного стандарта, процесс настолько болезненный, что стандарт активно используется не смотря на то, что они окончательно устарели. В качестве вопиющих примеров можно вспомнить Z39.50, SMTP, FTP и HTTP. К проектированию стандартов имеет смысл относиться даже более внимательно, чем к проектированию баз данных. "Внимательно" в данном случае означает не "предусмотреть все возможные случаи", а обеспечить возможность изменений. Все равно предусмотреть все не удастся, а если и удастся, то этим все равно не станут пользоваться из за непомерной сложности.

Код

Срок жизни кода определяется сроком жизни требований и сроком жизни платформы. В любом случае, срок жизни прикладного кода составляет 5 -- 10 лет. К этому моменту он оказывается практически полнотью переписанным с нуля. Часто, код преписывают весь сразу, одновременно с переходом на современную платформу. Конечно, бывают и исключения. Чаще всего они связаны либо с неизменными в течение десятилетий требованиями, либо с очень высокой ценой апгрейда. Например, связанного с высокой ценой миграции данных. Код ядра живет дольше в силу того, что зависит не от зыбких пользовательских требований, а от технических ограничений. Однако и технические ограничения меняются: если раньше несколько процессоров встречались только в серьезных серверах, то теперь многоядерные процессоры добрались до ноутбуков. Даже если завтра ваши алгоритмы и не изменятся, не исключено, что им придется работать совсем в другой среде, что влечет за собой переписывание кода.

Абстракции и модели данных

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

Пользовательский интерфейс

Пользовательский интерфейс протухает за 3-5 лет. Он подвержен тем же изменениям требований что и код, вдобавок новые интерфейсные технологии появляются ничуть не реже программных. Даже отличный интерфейс пятилетней давности выглядит малость устаревышим, а десятилетним интерфейсом современному человеку пользоваться неудобно, да и глаз режет. Метафоры за 10 лет успели сильно измениться. Если пользователи не могут сбежать, устаревший интерфейс удается сохранить два-три срока. Затем начинаются проблемы уже с поиском операторов, способных работать на таком старье.

четверг, Сентябрь 25, 2008

ICFP Contest '08 Final results

На официальной странице ICFP Contest выложены результаты, которые так долго ждали большевики. Было проведено 11 заездов, в результате которых был определен один победитель (Team Smartass) и 297 неудачников, которым не так повезло. К сожалению финальные карты еще не выложены, поэтому трудно сказать что пошло не так, но финалисты предыдущего чекпойнта "вылетели за ограждение". Как в прошлый раз, я подготовил таблицу с суммарными результатами. Команды отсортированы по количеству раундов, в которых они приняли участие независимо от результата. Команды, прошедшие одинаковое число раундов отсортированы по рейтингу. Напоминаю, чем меньше рейтинг, тем круче. Для каждой команды приведена статистика исходов по всем пяти заездам каждого раунда. В общем, можно меряться. Get it and use it well.

Моя команда называется Mosquito. Каким чудом она попала на 11 место, оставив позади страшных монстров, сам не понимаю. Видимо, новичкам везет.

#TeamRoundsScoreHomeMartianCraterTimeoutError
1Team Smartass11512510505
2shinh115153704951
3Error 404115419605032
4UBE11546000487
5LazyBear115568705122
6SzM1160863040555
7souris aveugle1161162040123
8frank3241164361039655
9kstm.org1167453040132
10fireinthedisco2116894004582
11Mosquito1173004041851
12Om Nom Nom Nom1174314037153
13Giantslalom1174855038161
14epriestley1176509033175
15intelliarts1060905037814
16cw106170704010
17The B-Team: 25/26ths as good as the A-Team1061928040145
18Blue Iris106268603713
19Spore Sept 7th, only $49.99! Play Bejeweled @ popcap.com!10631580381011
20team_bruno10649780419
21Hands Solo106522004082
22jabber.ru106543103713
23Celestial Dire Badger10659590446
24Side Effects May Include...106607403812
25Apathy Kings10665890361211
26CNaml106728103713
27Cup<'t>1069525036131
28TC2107033104010
29Team Meh107104303812
30Yeahbut10712870437
31td107169504271
32Purple Pointer Eaters107195603515
33TeamDJ1072120036131
34ur 67P1072335032171
35NMSU107327703911
36Actua107390203416
37Eger a Marson1073954035132
38EdFred1074258038102
39Arekuma1074803035132
40little lemon1078496034142
41Order of the Fridge108053103317
42HackerDom_194421503510
43ais5239442380387
44ILL martians94483003411
45Sir Bedevere the Wise94507803492
46Kee9455360369
47Urxae946507034101
48Heklers94657903384
49Malfunctional Programmer94702503510
5042947790033111
51Slow9478020369
52LUHPI94842903672
53tidder948657034101
54elbereth@utmc9487230378
55Wile E.94923003591
5612a094941803114
57PurelyFunctionalInfrastructure95015203411
58RHZ95015703672
59m1-speedygonzalez95151803411
60Five of Six951680030762
61Bobry9543260294111
62a1k0n955337028134
63Team Sampou957250030141
64taxi driver839880029101
65BugbearR84110603451
66Dee Mon8428540346
67ayatuki84333502695
68HackerDom84342102812
69Too Simplicity and Beyond!843892026941
70I-cons-a-lot84487702992
71The Dibbies844886023116
72Hacking in the Rain845433024781
73Altair84625502992
74lazymonkeys846802030631
75'a infvec84712902875
76protocolocon847215031414
77Kharkiv MIND84798102785
78Begot85010702515
79Lazy elf8509630231061
80astsmtl7313950278
81shitamachi no ue73195602771
82kounoike7323950287
83Java Jones and the Kingdom of the Crystal Crater73315202672
84TBD73319802510
85lepidum7333640278
86ktkr-cpp733909026621
87miyu73412203041
88Gcup73415602681
89Epsilon73532502942
90nanndemoiidesu73556702591
91pirapira73572002510
92barry, our driver, is reckless73665102591
93NAU ACM73724902195
94TheRoverers73732102411
95DotWeb74033302096
96SwtPl740343021104
977-15741668022121
98Beer:Thirty626351024321
99Team DumbAss62785302181
100inforfun6278540246
101Team Lolemnity628437021522
102ntua 67P62855002343
103jan nasa62952702352
104Pear Programmers62958502442
105Christoph Breitkopf6297470246
106spotrover629798021351
107cashto62984502253
108The Weyburn Expatriates62999102235
109ORBIT63013202424
110Rhope Burn63018202325
111aruhimorinonaka63020202271
112green_tea63035702442
113Bob's Store63058702226
114WindowMakers 63076002271
115The Blind Hen63079902262
116bmm team63095702424
117Grasshoppers63098602163
118The Tcler632061020361
119ksk63215002127
120MIMUW 406063252602262
121Florida Institute of Technology63254102253
122D&D632740018372
123wjdogs63282601758
124Kerochan63291802073
125The Unchecked Exceptions63299302019
126In dumb we trust63350401974
127Curry On!633519017364
128KFL633554021252
129hibi@utmc.or.jp633664021351
130YBuzz633863020361
131Dragons633921018381
132Q42/Xopus634184018471
133Team Guyford63420301812
134Arsbit63512101857
135one canuck63545101776
136Chouser635591018372
137uguu.org63566901848
138midoj636782019641
139The Tweezer Minstrels63709601578
140bens63730001785
141apple2gs63787902154
142yarunee638188016383
143The Usual Suspects63820802136
144Ramen Holiday638355019461
145The Code Alchemists63847902181
146Team Rocket63893201947
147nekoneko 639315017571
148The Inmates63937702073
149camping gaz international63977902226
150solo r6640265020811
151GRoboCode64033401938
152ktkr-ocaml64119901857
153LazyBottoms644571016671
154spbsunt5176870214
155It's all about the Pentiums.51832901933
156Emory PChem51842701951
157Toasted Monkeys518614019222
158Le club des 551887501942
159suihan_jar519344017431
160Wobbla Team51939802041
161__ufo42520548013264
162Dis Functional52095501546
163POSTECH-PL52100901654
164The Higher Order Of Zeuxis521291017332
165Unary Operator52141701843
166POSCAT@POSTECH522283014254
167suzumiyaharuhiko522405011743
168Hidden Agenda4147770146
169Incompetent Design414821011531
170OCamlCore41530501253
171Knights of Cydonia41590501253
172Marcin Simonides4160540128
173td241606201334
174efg416122013331
175AntiCylonDefenseTeamImpersonator41616501262
176ikon416273010343
177o(ry41644701451
178bucchigiri41652301325
179Dylan Hackers41653101352
180Team Gales416570011252
181The Rover Routers416690013511
182Anairiats416719014321
183Tigerfunk41708406284
184dot-emacs41737807283
185Fly (Yaroslavl)41758001271
186K&R41758401334
187Mostly Harmless41784901271
188AyaCFP4178530137
189putzen along41787401271
190Enoch Root417978011531
191futurelabs41809901244
192Molotov Mocktail41864309722
193Servants of Barsoom4187290128
194NetHack41875501262
195Ruby Team4187930128
196Almaya418813012521
197gassa & toxa41930001172
198(defun friends)31071801032
199The Lone TeXnician31077008232
200hogelog3108370663
201Insane Closure Posse3111800114
202Macrott31133109321
203Blazing Saddles31153709312
204yet another team31155507413
205honey_rooibos311614096
206Evil Geniuses For a Better Tomorrow31173601041
207TeamNewshamBros3117630924
208Illudium Q-36 Explosive Space Modulator31180609411
209Giver3118500924
210rmathew31191205253
211SIMAP31195709321
212eugene_jeff31222406423
213polka31243008421
214Func-n-stein31251407242
215EddieHasNoPreferenceForName 3126480852
216Xebia31281108331
217Bad Science3129430861
218Stern Types 31304007323
219siti31324707611
220panard_groumpf31343805334
221SugarSun3134660861
222mfp31358604515
223NCSU ARC Alums3136960933
224The Bobcat Hackers31389806522
225Knights of the Crescent Moon31402505424
226isobe31406607431
227EarthFusion31443108511
228Epic Fail31467506522
229plai31476205622
230ozy4dm315737078
231wheezards257930811
232Soul Trader2775804213
233404 NOT FOUND2784703151
234WE NEED A TEAM NAME2785406211
235Not a Number2789105212
236Stanfy279440712
237Bloody Camls27950073
238Team Sparrow279740631
239Too much free time280430622
240Linkage Failure28066073
241kt3k28123073
242Suzumiya Haruhiko wo Ooini Shizumeru Fullbocco-dan281960631
243University of Western Australia283980622
244Littlechina2848305311
245Drifter's Revenge2851505212
246Erraen285860631
247cthulhuivore2869402134
248ktkr-java2893904213
249Ocamlman2895005221
250Team Cow290130622
251Rhinos290200118
252Cup<T>292040631
253The Chun Council29234064
254FUN292460451
255ICSkies of Blue and F(P)2925504231
256Felspar292560631
257Happy Camels292670631
258The Teddyborg2928502314
259drunken ants2928605221
260foognostic292950127
261Marti293070631
262StreetMagic294650622
263Cal Poly Pomona Computer Science Society29753064
264nishiohirokazu29851064
265United Coding Team29888055
266KuntbucketsAndKuntrags2100630136
267Turn Right Left210067055
268mazeSolver@UTMC2102330343
269Schwarzschild2107120532
270gpfault id-alex 2107250244
271aalto high school21153201513
272The Dudes2115510352
273Engineers Without Boulders21167104411
274The Al-Gore-Rhythms AKA The Doug Boat21177001315
275Team_XIII 211920055
276The Armstrongs2124310514
277casillero del diablo2125570154
278gzoluble213069055
279Chvex Stucture2148470145
280SATiriker136160131
281The unmoving notogawa1423005
282Monkeyget1423005
283Sim1423005
284P Squared1423005
285gb1423005
286mokehehe 1423005
287ocaml users anonymous1423005
288LISA~HackLab-FI1423005
289zetafish1423005
290Puddingforce1423005
291Chicago Blubs1423005
292Nodal Asymmetry1840005
293incognito1840005
294Monadic Cows1840005
295Late Ocamler1840005
296Rufus21840005
297greedy1840005
298The Shiniest of Heisenbugs1840005

понедельник, Сентябрь 08, 2008

Закон больших чисел

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

На большой выборке даже маловероятные события становятся наблюдаемыми.

На практике этот закон означает полную неприменимость «наивной» аналитики и, как следствие, «наивного» тестирования при проектировании информационных систем. Если не предусмотреть редкие случаи ещё при проектировании они больно стукнут на стадии эксплуатации, причем далеко не сразу, а лишь по прошествии некоторого инкубационного периода. Это чревато хотя бы тем, что багфиксинг на внедренной системе, в которой уже накоплен значительный объем данных — отдельное развлечение.

Ещё одно проявление Закона больших чисел в том, что невозможно построить информационную систему гарантированно не содержащую ошибок в данных. Простой пример: Оператор вводит данные вручную. Оператор не идеален, поэтому он делает одну ошибку на 100 записей. Это означает, что на 1 000 000 введенных записей будет порядка 10 000 ошибок. Поскольку такое количество ошибок нас не устраивает, мы садим поверх оператора контроллера, который будет проверять правильность ввода. Пусть контроллер более внимателен и продуктивен, однако и он не идеален, поэтому допускает одну ошибку на 1000 записей. Тогда вероятность ошибки снижается до 10-5 на запись. Однако, на миллионе записей это даст примерно 10 ошибок. Если количество данных неограниченно растет, а так бывает почти всегда, никаким контролем не добиться гарантированного отсутствия ошибок. Даже оценить вероятность ошибки и то не всегда возможно. Люди не механические приборы, к ним паспортов точности не полагается.

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

  • Признают, что качество данных не имеет значения для бизнеса;
  • Контролируют качество собственными силами;
  • Выбирают один из наборов данных и признают его эталонным.

Это всего лишь частные эффекты. На практике достаточно хорошо осознавать, что чем больше данных, тем сильнее проявляется Закон больших чисел, влияние которого нужно учитывать при проектировании, в разработке и в тестировании.

понедельник, Август 11, 2008

ICFP '08 Results

Опубликованы результыты первых восьми заездов. Для удобства фаллометрии свел все в одну табличку. Get it and use it well.

Score — сумма по всем восьми заездам.

Команды не допущенные до девятого заезда в табличку не включены.

UPD: Добавил восьмой заезд. Плюс организаторы вернули еще 16 команд, дисквалифицированных по техническим причинам.

TeamScore
1UBE327090
2td329520
3Celestial Dire Badger330350
4Hands Solo330560
5Blue Iris331800
6Team Meh332900
7shinh333270
8NMSU333390
9team_bruno333590
10Team Smartass334470
11CNaml334680
12Error 404334770
13cw336130
14HackerDom_1336740
15Actua337670
16ILL martians337870
17Yeahbut338630
18fireinthedisco2340290
19ais523340450
20Arekuma341070
21TC2341190
22elbereth@utmc341290
23Spore Sept 7th, only $49.99! Play Bejeweled @ popcap.com!341510
24Apathy Kings342900
25LazyBear347940
26SzM348090
27Wile E.352650
28Sir Bedevere the Wise353750
29TeamDJ353980
30Kee355170
31jabber.ru356170
32frank324356270
33Urxae358030
34Malfunctional Programmer358770
35Heklers359580
36PurelyFunctionalInfrastructure361340
37Cup<'t>362370
38Side Effects May Include...362960
39Purple Pointer Eaters363780
40intelliarts365870
41Slow366260
42EdFred367150
4342367510
44The B-Team: 25/26ths as good as the A-Team371520
45a1k0n373610
46RHZ373950
47souris aveugle374140
48LUHPI374310
49little lemon375620
50kstm.org376070
51m1-speedygonzalez377810
52Team Sampou378210
53Five of Six378920
54Mosquito381240
55Eger a Marson381530
56ur 67P385050
57tidder385790
5812a0389440
59Giantslalom390270
60epriestley408520
61Om Nom Nom Nom409070
62Bobry412030