[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Re: Несколько вопросов вразброс



Артём Н. -> debian-russian@lists.debian.org  @ Wed, 04 Jul 2012 20:04:14 +0400:

 >>  >>  АН> А как доказать корректность сложной функции, которая образует
 >>  >>  АН> систему простых?  Как проверить все связи?  Как доказать
 >>  >>  АН> корректность функции с побочными эффектами?  И, например,
 >>  >>  АН> "крайний" случай: возможно ли доказать корректность поведения
 >>  >>  АН> произвольной ИНС?
 >>  >> С тех пор, надо сказать, наука шагнула довольно далеко вперед, и
 >>  >> рутинные операции типа проверки _всех_ связей компьютер делать уже
 >>  >> обучен.
 >>  АН> ...
 >>  >> А теория нам говорит, что нельзя построить универсальный автоматический
 >>  >> доказыватель программ.  А того, что нельзя доказать конкретную
 >>  >> программу, даже довольно сложную - не говорит.
 >>  АН> А на практике? Ведь программа взаимодействует с окружением. И
 >>  АН> окружение, и программа могут иметь такую сложность, что проверить
 >>  АН> все пути не представится возможным..?  Я не бросаю камень в сторону
 >>  АН> автоматической проверки корректности (о которой и хочу
 >>  АН> узнать). Просто мне кажется, что отказ от тестов - не самая лучшая
 >>  АН> идея.
 >> 
 >> На практике же основная проблема тестов заключается в том, что они сами
 >> содержат ошибки и часто тестируют не то, что надо
 АН> Тесты для тестов... >< Тесты, в принципе, должны быть просты и
 АН> малы, как мне кажется.

Тогда они не покроют код.

 >> а сколь-нибудь
 >> серьезно покрывающий код набор тестов занимает в разы больше места, чем
 >> сам код
 АН> Ну, не знаю больше ли, но соотношение явно не самое оптимальное. :-(

Больше.  В разы.  Потому что надо подсунуть коду хмурую тучу комбинаций
значений, особо уделяя внимание всяким краевым случаям (типа если
параметр a должен быть в пределах от 0 до 5, а b - от 7 до 12, то нужно
давать все комбинации из набора [-1,0,1,4,5,6] для a и [6,7,8,11,12,13]
для b.  Ну, грубо.  Нет, скомбинировать по одному нельзя - ты
скомбинируешь -1 с 6, а бага спряталась в комбинации -1 с 8.)  Да, при
этом будет некоторый шаблон, и можно запустить два вложенных цикла.  Код
тестов будет еще ничего, просто сравним с тестируемым кодом (но меньше
уже не станет).  Но когда параметров наберется десяток, время выполнения
тестов станет уже недопустимо большим.  А кроме того, в случае тестов со
вложенными циклами довольно трудно потом прогнать ровно тот тест, на
котором оно падает.  То есть под это надо специально точить тестовый
фреймворк, и уже он становится больше тестируемого кода размером.  А
потом ты заметишь, что помимо теста на успешную регистрацию, надо
сделать тест на занятый логин и на недопустимый пароль (у них разные
сообщения об ошибках, поэтому это разные тесты; ну и тест на
недопустимый пароль - это тоже цикл, а не один тест).  И каждый из них
имеет примерно тот же размер, что тестируемый код.  Вот тебе уже тесты
втрое толще тестируемого кода.

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

 >> Так вот, я не поручусь, что агда тебя заставит доказать программу.
 >> Скорее всего, не заставит.  Но то, что она согласится скомпилировать,
 >> будет надежнее, чем то, что ты сможешь автоматически оттестировать за
 >> разумное время.  Ключевое слово тут "автоматически" - ручное
 >> тестированние может открыть много нового.
 >> 
 >>  >>  >>  >>  >> Любой статически типизированный функциональный язык с нормальной
 >>  >>  >>  >>  >> системой типов, начиная с того же Haskell или Ocaml.
 >>  >>  >>  >>  АН> Ocaml? Любопытно. Пожалуй, посмотрю подробнее.
 >>  >>  >>  >>  АН> Для него есть какая-то IDE? И как с библиотеками?
 >>  >>  >>  >> Я знаю одну IDE на все случаи жизни.  Emacs.
 >>  >>  >>  АН> И для всяких там GUI? ;-) В общем, я им не пользуюсь.
 >>  >>  >> Ну да.  Поскольку мои дизайнерские способности ниже средних, в отличие
 >>  >>  >> от способностей в разработке поведения, я предпочитаю GUI, которые
 >>  >>  >> пишут, а не рисуют.  Внешний вид - дефолтный, а поведение описывается
 >>  >>  >> словами.
 >>  >>  АН> Дык, "внешний вид" - это не картинка кнопки, а компоновка. Всё же
 >>  >>  АН> словами не опишешь. Видеть надо.
 >>  >> Компоновка как раз очень неплохо описывается словами.  Заодно потом не
 >>  >> возникает типичных для мышконавозенного гуя ситуаций, когда при переводе
 >>  >> на русский половина надписей получается обрезанной, и в лучшем случае -
 >>  >> поперек, а то я у фотошопа видал, что видно нижнюю половину одной строки
 >>  >> и верхнюю - другой...
 >>  АН> Я понимаю, что практически любой интерфейс описывается словами. :-)
 >>  АН> Такой же язык. Но создавать его, описывая словами, мне кажется не
 >>  АН> самой лучшей и перспективной идеей.
 >> 
 >> А зря.  Если описывать его поведение словами, предварительно подуманными
 >> головой, а визуал оставить на простенькую автоматику, то... выглядеть он
 >> будет не шедеврально.
 АН> Выглядеть - в плане?

Ну вот тебе не нравится интерфейс, сделанный на Tk.  Внешне.  Типа,
gtk'шный круче.  С виду.

 >> Зато им будет удобно пользоваться.  А от
 >> интерфейса, о чем современные мышевозильцы под давлением маркетологов
 >> обычно забывают, требуется именно удобно себя вести, а не красиво
 >> выглядеть.  Иначе непонятно, зачем он вообще нужен - если ты хочешь
 >> красивого, выведи себе xsetroot'ом на весь экран картину Рериха, и сиди,
 >> наслаждайся...
 АН> Построение интерфейса не сводится к его описанию.
 АН> То, как он выглядит, нельзя отделять от того, как он себя ведёт.
 АН> "Красота" должна тоже быть.

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

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

 >>  АН> C прост и элегантен. :-)
 >> Прост и элегантен, если мы говорим о языках уровня C, Pascal.  Если
 >> говорим о скриптовых - tcl.  А C - это язык, сделанный практиками для
 >> себя, и простота и элегантность его, как и у Perl, весьма умеренны.
 >> Элегантность в жертву практичности и те, и другие приносили без
 >> содрогания.
 АН> Ну да, только практичность включает элегантность и простоту.

На практике все хорошо в меру.  В том числе элегантность и простота.

 >> Вот C++ получился еще и непрактичным.  Хотя лемминги пользуются.
 АН> Да и не только они. Но C++ - это что-то монструозное. Кстати, ведь
 АН> он ещё и функциональную парадигму включает сейчас?

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

 >>  АН> А про Perl ходят шутки:
 >>  АН> "Любой набор символов в любой кодировке является синтаксически правильным Perl 6
 >>  АН> кодом.
 >>  АН> Всегда есть бесконечное количество различных способов сделать это.
 >>  АН> Любой человек, писавший до этого на любом языке, может сразу писать на Perl 6.
 >>  АН> Он может даже не догадываться, что пишет на Perl 6. Если, конечно, не будет
 >>  АН> забывать ставить 1; в конце модулей.
 >>  АН> Можно перегружать 1;. Можно перегружать пробелы. Можно перегружать сорц фильтры
 >>  АН> с помощью регулярных выражений, которые тоже можно перегружать.
 >>  АН> Perl 6 имеет эталонную реализацию, написанную на Perl 6 и не способную быть
 >>  АН> выраженной ни на каком другом языке. На Perl 6 эталонная реализация может быть
 >>  АН> выражена, но не за конечное время. Мы работаем над этим.
 >>  АН> 1;"
 >>  АН> ...
 >>  АН> "Программы на Perl могут писаться на любых языках, например на латыни или языке
 >>  АН> Древних. О написаніи программъ въ орѳографіи образца 1916-аго года покамѣстъ
 >>  АН> свѣдѣній нѣтъ.
 >>  АН> Perl — один из немногих языков c поддержкой квантового исчисления."
 >> 
 >>  АН> Про C - это бы звучало дико. :-)
 >> 
 >>  АН> "Та часть, которая делает Perl языком Perl, умышленно построена на смеси разных
 >>  АН> парадигм, учитывающей каждую из них. Можно сказать, что Perl не собирается
 >>  АН> навязывать вам никаких догм. "
 >>  АН> Лари Уолл.
 >> 
 >> Последнее - это правда, и я считаю это достоинством этого языка для
 >> меня.  Сам я чаще использую функциональную парадигму плюс обработку
 >> исключений, но это потому, что я сейчас чаще пишу на нем скрипты.  Писал
 >> бы толстые приложения с плохо заданными требованиями - была бы
 >> объектная.
 >> 
 >> А остальное - просто шутки.
 АН> Но в каждой шутке...

Есть доля юмора.  Да.  В вышепроцитированных она довольно высока.

 >>  >> Для задач, которые можно решать на sh, этого достаточно.  Ну, может, еще
 >>  >> IPC::Open2 и IPC::Open3, когда надо и на вход подавать поток, и на
 >>  >> выходе его забирать, да еще (в случае Open3) stderr анализировать.
 >>  АН> Не знаю, может Perl и хорош. Но Camel Book, о котором тут писали на 1000 с
 >>  АН> копейками страниц? И тогда уж сравните с книгой K&R...
 >> Зато между объемом кода и временем для решения одной и той же задачи
 >> разница будет в противоположную сторону, и куда больше.  Книгу ты
 >> читаешь один раз (потом можешь обращаться как к справочнику, но тут уже
 >> объем мало влияет).  Код пишешь (предположительно) многократно.  Дальше
 >> думай сам.
 АН> Дело не столько в количестве часов, потраченном на книгу, сколько в
 АН> том, что оба языка позволяют сделать одно и тоже.

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

 АН> А основной "мануал" отличается на порядок по размеру. Это о чём-то
 АН> говорит...  Насчёт времени и объёма - не согласен. Всё решают
 АН> библиотеки.

С библиотеками всё решает количество телодвижений, необходимых для того,
чтобы ими воспользоваться.  Сравни количество телодвижений для того,
чтобы поработать, скажем, с MySQL-базой на libmysqlclient и на перловом
DBD.  А потом попробуй переехать на PostgreSQL или на sqlite.

Когда вынырнешь - возьми хоть тот же gtk.  Когда вынырнешь и оттуда -
добавь сетевой протокол.

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

 >>  >> Пока я не стал большим любителем ОС Emacs, я пользовался tkabber в
 >>  >> качестве jabber-клиента.
 >>  АН> Этот тот, у которого суровый серый интерфейс? o.O
 >> Да.  Но можно раскрасить в несколько строчек конфига.  Мне было не надо,
 >> он мне для разговоров словами был нужен, а не для любования.  А в
 >> разговоре чаще важно, чтобы ничего, в том числе попугайская раскраска,
 >> не отвлекало от темы.
 АН> И ещё он всегда выглядит в стиле tk, где бы не запускался: великое
 АН> единообразие. :-)

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

Диалоги он, впрочем, дергает системные.  В тех системах, где такое
понятие есть.

 >>  >> Остальные, сделанные на мейнстримных языках
 >>  >> для разработки Настоящих Приложений(tm), прямо скажем, существенно хуже,
 >>  >> существенно менее надежны, и в случае, когда ненадежность таки
 >>  >> срабатывает, их куда сложнее починить.
 >>  АН> Возможно. Только имеет ли это отношение к языку, в данном
 >>  АН> конкретном случае?
 >> Имеет.  Потому что предлагаемый языком способ выражения мыслей очень
 >> сильно влияет на эти свойства.  Программу-то пишет человек.
 АН> Но человек выбирает язык (в идеале)... Всего-лишь инструмент. И, в итоге,
 АН> всё-равно получается другой язык, только синтаксически связанный с тем на
 АН> котором он пишет (особенно это хорошо видно в случае с Forth).

Человек выбирает язык из того набора, которым владеет.  Если человек
владеет только молотком, он будет и шурупы им "завинчивать".  С
соответствующим результатом.

 >>  >> А что не широко - так надежные средства надежны потому, что работают на
 >>  >> другом уровне абстракций.  Типичный индус(tm) такой уровень собственным
 >>  >> мозгом не освоил, поэтому пользоваться ими тупо не может.  И не только
 >>  >> индус.
 >>  АН> На уровнях выше? Хм... Но есть шаблоны..?
 >> 
 >> Поднять компьютер на пару уровней абстракции выше сравнительно несложно
 >> (правда, то, как это делают правильно, обычно не называется шаблоном -
 >> хотя процесс, да, сводится к обнаружению шаблонов и выделению их в
 >> отдельные сущности).  Но если ты сам не освоил этот уровень абстракций,
 >> то способность компьютера справиться с ним не поможет твоей программе.
 >> Что с индусами(tm) и наблюдается.
 >> 
 >>  >> Тонкость с tkabber в том, что по крайней мере один из его ведущих
 >>  >> разработчиков - выпускник мехмата МГУ, и с уровнями абстракций у него
 >>  >> все хорошо...  Поэтому ему на tcl удобно.
 >>  АН> И причём тут Tcl? :-)
 >>  АН> Вопрос в том: почему Tcl - личные пристрастия, исторически так
 >>  АН> сложилось или чем-то обоснованный выбор?
 >> Ты хотел простого и элегантного синтаксиса.  Проще и элегантнее я не
 >> знаю. 
 АН> Я хотел (и хочу) надёжного и быстрого ПО, которое может быть
 АН> написано сравнительно просто, быстро, без акцента на языке и
 АН> сильного напряжения. :-)

Так чего ж ты тогда от перла отмахиваешься?  У лиспов и tcl порог
вхождения выше, хорошо бы иметь высшее образование в Computer Science
(не обязательно, но хорошо бы).  Для быстрого вхождения в Haskell хорошо
бы иметь в Computer Science уже степень, причем защищенную не на
реферате, а на самостоятельной работе - иначе вхождение в него занимает
годы.  А вот перлом до запрошенного тобой уровня можно овладеть довольно
быстро.

 >> Сравнимого - ну, может быть Scheme.  Кстати, она - прекрасный
 >> пример к предыдущему блоку квотинга в этом письме - научить компьютер
 >> обращаться с call-with-current-continuation оказалось несложно и очень
 >> недорого.  А вот я при всем своем математическом образовании с этим
 >> инструментом так и не сумел освоиться пока.  (Все эти ваши исключения и
 >> прочие нелокальные переходы, не говоря уже о вызовах функций, if и
 >> циклах могут быть представлены как частные случаи работы с continuations
 >> и выражены через call/cc, и это далеко не все, на что способна эта
 >> абстракция).
 АН> Scheme - это почти Lisp или нет?

Это один из диалектов лиспа.  Довольно сильно отличающийся о классики
(что от исходного, что от Common).  Сознательно урезанный в синтаксисе и
семантике для того, чтобы можно было быстрее осваивать.  Макросы там
появились не сразу, и их там недолюбливают (и прямо скажем, есть за
что), зато там давно есть call/cc, которой в явном виде нет в остальных
лиспах.

Собственно, для человека с бэкграундом в C и sh call/cc окажется в
scheme единственным серьезно незнакомым оборотом, функция как
first-class object осваивается быстро.  Зато ОЧЕНЬ СЕРЬЕЗНО незнакомым.

 >>  >>  >>  >>  >> OPT_PARAM1=${OPT_PARAM1:-value1}
 >>  >>  >>  >>  >> и позволить пользователю переопределять именно OPT_PARAM_1,
 >>  >>  >>  >>  >> использование которой он потом увидит, а не неочевидно с нею связанную
 >>  >>  >>  >>  >> ENV_USER_PARAM1
 >>  >>  >>  >>  АН> Проверять наличие в окружении OPT_PARAM перед чтением конфига.
 >>  >>  >>  >>  АН> И записывать во внутреннюю переменную. Затем делать подстановку переменной по
 >>  >>  >>  >>  АН> умолчанию, взятой из конфига.
 >>  >>  >>  >> А чего ради так извращаться, если есть более прямой путь?
 >>  >>  >>  АН> Чтобы не усложнять конфиг и не вносить в него код. Не делать его неочевидным, не
 >>  >>  >>  АН> увеличивать в размере и, следовательно, не усложнять для изменения
 >>  >>  >>  АН> пользователем. При этом, гибкость почти не уменьшится.
 >>  >>  >> Если конфиг надо писать пользователем, то опять же, возьми tcl.
 >>  >>  АН> Ну, а в чём будет разница?
 >>  >>  АН> Тут дело же не в реализации, а в подходе...
 >>  >> 
 >>  >> Разница будет в том, что у tcl язык задания переменных куда более
 >>  >> человеческий.  Программисту пофиг, а пользователю - нет.  (Я вот тут
 >>  >> сейчас по работе смотрю на описание функционала в cucumber, который
 >>  >> позиционируют как инструмент даже не для TDD, а для B(ehavior)DD - так у
 >>  >> него стиль описания еще более человеческий, и в комплекте штатные
 >>  >> переводы ключевых слов на N языков.)
 >>  АН> Тэкс, интересная штука. Сейчас ознакомлюсь.
 >> Глянь.  Там сам-то инструмент простенький и, прямо скажем, глючноватый,
 >> но идея, что можно иметь описание поведения, понятное и (требует
 >> написать дополнительные определения, но не шибко сложные) автоматике, и
 >> заказчику, вплоть до возможности позволить минимально обученному
 >> заказчику самостоятельно описывать это поведение, имеет довольно далеко
 >> идущие последствия на пути к получению _нужного_ результата.
 АН> Примерно понял что это такое: TDD на процесс проектирования.
 АН> Условия прохождения теста - пользовательские требования. Модуль -
 АН> единица достаточная для прохождения одного теста. В сравнении с
 АН> TDD, модули большие, а тесты интегративные. Плюс - человеческий
 АН> язык описания.
 АН> То?
 АН> Но ещё читаю.

Чисто технически - да.  Но опять же напомню про машину Тьюринга.  Все
языки программирования, кроме машинных кодов - они не про объяснение
компьютеру.  Они про объяснение человеку, про процесс разработки.  То же
и тут.  Если огурца интерпретировать как TDD с человеческим языком, это
будет один процесс разработки.  Если как BDD - другой.

 >>  >>  >>  АН> 2. Это просто обработка значений. Переменная как влияла на
 >>  >>  >>  АН> подмножество действий/объектов, так и влияет. Размер
 >>  >>  >>  АН> подмножества не расширяется.
 >>  >>  >> Э, нет.  Она начинает на него влиять куда как более
 >>  >>  >> обусловленно.  "Если выполняется это условие, проверяемое в
 >>  >>  >> 235-й строке, но не вон то, проверяемое в 538-й, то влияет, а
 >>  >>  >> может, и нет..."
 >>  >>  АН> Ээээ... Не очень вас понял. Есть переменная.
 >>  >>  АН> Она влияет на определённое подмножество объектов.
 >>  >>  АН> Её возможно задать.
 >>  >>  АН> Задаётся она один раз.
 >>  >>  АН> Задан она может быть в конфиге или в переменных окружения.
 >>  >>  АН> Это понижает ортогональность (ради повышения настраиваемости), поскольку есть
 >>  >>  АН> две точки входа, вместо одной - конфига.
 >>  >>  АН> Есть два варианта реализации:
 >>  >>  АН> 1. Обработка в конфиге.
 >>  >>  АН> 2. Обработка в основном коде.
 >>  >> 
 >>  >>  АН> При обработке в конфиге, есть ощущение того, что остаётся одна
 >>  >>  АН> точка входа - конфиг. Реально, как две точки было, так две и
 >>  >>  АН> осталось.  Просто часть логики перелезла в конфиг. Что его
 >>  >>  АН> усложнило.
 >>  >> При этом в конфиге _все_ переменные обрабатываются _единообразно_.
 >>  АН> Ключевое слово - "обрабатываются". Код в конфиге.
 >> Ну, да.  Если мы говорим о шелле, то создать язык конфига, который можно
 >> писать с какими угодно ошибками, и они будут корректно обработаны - это
 >> плохо реализуемая задача.  У шелловских скриптов конфиг, как правило,
 >> исполнимый.  И я давно уже этого не пугаюсь.  Задача конфига - быть
 >> понятным человеку.  _Умеренное_ количество кода там этому не
 >> противоречит.
 АН> Возможно. Но, всё-таки, если переменных много, проверки будут загромождать
 АН> конфиг и уменьшать читаемость.

:=

 >> Но я бы
 >> предпочел, чтобы из конфига и мана было ясно, какие значения будут где
 >> работать вот у такого вызова, а какие - у эдакого, и как задать вот это
 >> вот таким.
 АН> Комментарии? :-)

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

 >>  >> Нет, у тех, кто делает такие системы конфигурации.  Начиная с виндового
 >>  >> реестра, и заканчивая гномовским, и еще кем-то у нас в дистрибутиве же,
 >>  >> кто ради не помню чего, чуть ли не тоже конфигурации, тянет за собой
 >>  >> персональный экземпляр mysqld для каждого юзера.  Узнать о существовании
 >>  >> sqlite он, видимо, ниасилил...
 >>  АН> Дык, реестр - это БД. И sqllite - БД. И mysql - БД.
 >>  АН> Всё одно. Принципиальной разницы (на этом уровне) между ними нет: к
 >>  АН> одному они все и пришли.
 >> 
 >> Э, нет.  /etc/passwd и /etc/network/interfaces - это тоже БД.  Дьявол в
 >> деталях.  А в деталях...
 АН> Нет, это другое: в них нет главного - отношений. :-D Мда. :-(

Ошибаешься.  Отношения в них есть.  Не было бы в /etc/passwd отношения
между именем и uid - ты б залогиниться не смог.

 АН> БД - это именно структура связей. Реестр - иерархическая БД, всякие
 АН> *sql - реляционные, но везде есть отношения.

 >> - реестр - единая БД для множества никак не связанных между собой
 >>   программ, которая в результате оказывается труднообозримой и крайне
 >>   слабо пригодной для чтения или изменения человеком (а какая же она
 >>   после этого конфигурация, если чтобы в нее залезть, требуется
 >>   отдельная программа со специфическим интерфейсом, а чтобы разобраться
 >>   в том, что там содержится - отдел аналитики?)
 АН> Кстати, реестр - это отдельный сложный вопрос. Ведь он похож на
 АН> ФС. С некоторой точки зрения - иерархия в /etc тоже похожа на
 АН> реестр...  Основная разница в том, что ключи реестра нечитаемы для
 АН> человека (в том смысле, что там используются UID, глубокая
 АН> вложенность и низкая ортогональность (к примеру, информация о
 АН> расширениях, как правило, записывается в двух местах, а для чего?)
 АН> и т.п.).  И, вдобавок, реестр - лишняя сущность. Его функцию может
 АН> выполнять ФС.  Скорее всего, они создали его ради оптимизации:
 АН> ускорения доступа к большому числу настроек системы. Но я не
 АН> интересовался.  Если это так, то проблема не в реестре. А в
 АН> системе: "архитектура" реестра - прямое следствие из архитектуры
 АН> системы.

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

 >> - mysql же отличается от этих двоих тем, что это не БД, а СУБД.
 АН> Как и Sqlite. :-)

Ну, можно и так интерпретировать.  В зависимости от того, на чем
акцентировать внимание.  Если на том, что sqlite предоставляет
транзакционность - то да, а если на том, что СУБД - это отдельная
сущность, с протоколами доступа, желательно отдельным DBA, который умеет
ее настраивать и т.д., то нет.  Я акцентировал на втором.

 >>   Даже
 >>   если сравнить его с sqlite - вместо крохотной библиотеки, нужной для
 >>   чтения данных из файла, мы имеем нехилого размера демона, которому
 >>   отдельно надо настраивать права доступа (и не враз настроишь), который
 >>   весьма нервно относится к внезапной потере питания, данные из которого
 >>   надо бэкапить отдельным хитропопым способом, чтобы не побились, и
 >>   наверняка я еще что-то забыл.
 АН> Ещё несколько типов таблиц, транзакции, возможность работы, как модуля,
 АН> поддержка репликации и возможность построения кластеров. Ну и т.д..
 АН> Но на том уровне абстракции - они не отличаются. :-)

А главное, на этой задаче они все не нужны.

 >>   Он, опять же, хорош на своих задачах,
 >>   но если я вижу _персональный_ mysqld, я понимаю, что программами этого
 >>   разработчика пользоваться не следует даже начинать, лучше сразу
 >>   поискать, а то и написать альтернативу.  А то себе дороже выйдет.
 АН> Почему? Ну, например, программа тащит его в дистрибьютиве или
 АН> требует для установки (snort-mysql, например). Это же не значит,
 АН> что она обязательно плохо написана..?

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

Ну, я уж молчу про то, что о понятии "ноутбук работает от аккумулятора"
автор этой программы, вероятно, не слышал.

 >>  >>  АН> Ну а какие варианты, когда требуется такая сложная система?
 >>  >>  АН> Изобретать свой велосипед, в итоге сводящийся с СУБД?
 >>  >> Если такая сложная система конфигурации действительно требуется, то
 >>  >> уровень сложности самой задачи там запредельный.  Настолько
 >>  >> запредельный, что я, со всем своим опытом, сто раз подумаю, прежде чем
 >>  >> начать ее решать.
 >>  АН> Обязательно? А если это расширяемая задача. А разработчики проектируют
 >>  АН> "сверху-вниз", действуя на далёкую перспективу?
 >> 
 >> _Так_ проектируемая система не доживет до этой далекой перспективы.  А
 >> если доживет, то обнаружит, что на самом деле все совсем не так, как
 >> казалось много лет назад, на стадии проектирования.
 АН> Мда. Возможно. Тоже нужен баланс.

Да не возможно, а точно.  Предъяви мне хоть одну систему, которая так
проектировалась и до этой перспективы дожила.

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

 >>  >> И скорее всего, правильным решением будет не СУБД, и вообще не
 >>  >> конфигурация в привычном понимании, а протокол динамического
 >>  >> согласования, в духе какого-нибудь BGP.
 >>  АН> Хм... Типа, сети независимых агентов?
 >> 
 >> Смотря как определять зависимости.  Я бы как раз сказал "зависимых",
 >> имея в виду то, что связи между ними есть и важны.
 АН> В смысле относительно автономных.

В этом смысле да.  Иначе задача такого размера не будет решена никогда.

 >> СУБД, как правило, пытаются хранить свои настройки в себе же.
 >> Получается плохо :-)
 АН> Ну, в случае падения (но для этого есть другие решения). А так -
 АН> что плохого?

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

Короче, сходи на сайты MySQL и PostgreSQL и почитай, насколько там
развесистые конфиги, хранящиеся вне БД.  По крайней мере постгресовцы
точно пытались по максимуму втянуть конфигурацию в БД.  И всё, что
осталось снаружи - это то, что втянуть не удалось.

 >> Нет, я понял мысль.  Если у тебя вся логика в БД, то да, имеет смысл по
 >> крайней мере пытаться хранить там настройки приложения.  И то -
 >> настройки клиента тебе таки придется, скорее всего, вынести еще куда-то,
 >> а то он не сумеет подключиться.
 АН> Минимум, необходимый для подключения и плюс немного "сахара"
 АН> (достаточно общего).

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

 >> Но практика показывает, что хранимые
 >> процедуры - это далеко не самое удобное место для хранения логики.  У
 >> них обычно язык сильно ограничен, и реализация на них этой логики
 >> получается куда более геморройной, чем вне базы.
 АН> Но куда от них деться?
 АН> Они дают:
 АН> 1. Безопасность;
 АН> 2. Дополнительную надёжность;
 АН> 3. Часто - скорость;
 АН> 4. Унификацию интерфейса (что не на последнем месте, просто не всегда требуется).

 АН> И что, есть альтернатива (выделенный сервер приложений - не в счёт)?

Именно выделенный сервер приложений.  И только если ты упираешья в
скорость и хранимая процедура действительно позволяет ускорить работу (а
не наоборот, что тоже бывает) - то хранимая процедура.  Всё остальное
выделенный сервер приложений (вернее, сервер приложения - на каждое
приложение имеет смысл держать свой) обеспечивает лучше.  Даже
унификацию интерфейса к банальному выполнению SQL-запросов обеспечивает
никак не сама СУБД, а библиотека DBD :-)

 >> Опять же потому, что
 >> реляционная модель, или какая там будет модель у конкретной базы,
 >> подходит существенно не для всего - часть логики на нее обычно ложится
 >> нормально, а часть хреново.  И вот ту часть, которая "хреново",
 >> практически всегда стоит из базы унести.
 АН> Ну, понятно, что логика расчёта, которая почти не использует
 АН> значения из БД и которая не меняется со временем, при том, что её
 АН> реализация в виде хранимых процедур много сложнее реализации вне
 АН> БД, должна быть реализована в клиенте.

 АН> Я постарался всю логику (от расчётов, формулы которых возможно было
 АН> менять, а клиент имел обработчик, до добавления пользователей)
 АН> положить на плечи СУБД.  В итоге, получилось, как мне кажется,
 АН> достаточно неплохо (кроме размера, для небольшой задачи: только SQL
 АН> код процедур на 4k строк). Минус - не было тестов.  Их бы тоже
 АН> добавить в БД (и настроить к ним доступ только для root).  Всё
 АН> завалилось. :-) На тонком клиенте, который оказался не совсем
 АН> тонким (я полез реализовывать свой ORM, специфичный для задачи,
 АН> помимо штатного, реализованного компонентами MyDAC, что,
 АН> собственно, и дало большую часть кода и сложность, но, в итоге, -
 АН> упростило работу "бизнес-логики" с БД).  Конец немного предсказуем
 АН> - ни денег, не айс. И крайне неприятное ощущение: несмотря на
 АН> перетянутые сроки, приложение было реализовано процентов на 95. :-(
 АН> Там, конечно, были и другие причины, не связанные с процессом
 АН> разработки, но основные причина, которые мне пришли в голову, -
 АН> высокая сложность (структура БД была дана, как и предыдущее
 АН> приложение, пришлось заниматься "реверс-инжинирингом" :-), что есть
 АН> плюс: не совсем "с нуля", но и минус: с нуля и серьёзные
 АН> ограничения, плюс код для перестройки БД, которая уже работала) и
 АН> нечёткость спецификации.  Частично мне пригодилось (это дипломная
 АН> программка, которая, естественно, прошла), но основное
 АН> предназначение не выполнено.  _Крайне_ неприятно. :-(

 АН> Ещё хочется что-то делать, но очень хочется такого
 АН> избежать. Надоело. И вопрос - как?

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

Чего у нас там не совсем сырого и нормально доступного из нереляционных,
помимо BerkeleyDB? MongoDB только?

А идея пихать в базу данных бизнес-логику на практике показала себя
неудачной.  Или отдельный сервер приложения, через который клиенты ходят
в БД (более управляемая конструкция), или, если задача попроще, встроить
в клиента.

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

Если говорить о скриптах бэкапа, с которых мы начинали, то я бы
рекомендовал не TDD, а своевременное _корректное_ прерывание обработки
(возвращаясь к языкам - возьми perl или tcl, и не ленись кидать и ловить
исключения, на этой задаче это подходящий инструмент) с подробной
диагностикой (если perl - освой модуль Carp и функцию confess оттуда).
Особое внимание удели ситуациям, когда в случае ошибки имеет смысл
продолжать работать с другими данными (неполный бэкап все же лучше
отсутствующего), но донести до ответственного человека, что именно пошло
не так.

Потому что на задаче бэкапов важна не столько гарантия восстановления с
последнего бэкапа (ты все равно не можешь ее дать), сколько знание о
том, откуда что можно восстановить.  И как.

И кстати, еще большее внимание удели не скриптам бэкапов, а регламенту
обращения с бэкапными носителями.  Начни с предположения, что серверная
сгорела (ну, пусть хотя бы умер кондиционер, и она нагрелась до +60), и
подумай, откуда ты будешь в этой ситуации восстанавливаться.

И регламенту восстановления.  Включающему учебные тревоги.  Бэкап,
который просто есть, никому не интересен.  Интересен бэкап, с которого
можно (в смысле, достаточное количество людей действительно может)
восстановиться.

А то, знаешь ли, TDD на таких задачах очень легко дает _иллюзию_
работоспособности системы...


Reply to: