Суровый программизм

Вот читаю я, допустим, статейку про проект uTensor — совместимую с TensorFlow реализацию нейросетей для ARM Cortex M3 или M4.

https://towardsdatascience.com/why-machine-learning-on-the-edge-92fac32105e6

Штука прикольная — пусть и на «топовых», но все-таки на недорогих и довольно доступных микроконтроллерах позволяет, например, распознавать рукописный ввод:

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

Ну, для начала — математика. Для понимания хотя бы MIT’овского учебника по Deep Learning желательно иметь представление о линейной алгебре, теории вероятностей, возможно, о каких-то началах функционального анализа. Да, некоторые отрывочные сведения из этих дисциплин приведены в первой части этого учебника (так часто делают в американских учебниках — так как нет гарантий, что слушатели курса по машинному обучению перед этим действительно прослушали несколько курсов по математике) — но их явно недостаточно. Если ориентироваться на программу мехмата, например — это 2-3 курс, если безжалостно ужимать — то все равно необходимо 3-4 семестра одной только математики.

Программирование тут не менее суровое. Даже если предположить, что с Python (в объеме, необходимом для TensorFlow) человек, умеющий немного программировать на C, сможет разобраться самостоятельно — все равно здесь, как и в любом проекте с использованием микроконтроллеров, требуется отличное знание C и даже немного — C++ (даже если говорить о нем, как о C with classes — все же нужно понимать «цену» тех или иных возможностей C++). Не знаю, стоит ли в обязательные общие требования к программисту включать знания классических алгоритмов — но в целом в критичных к производительности задачах это оказывается само собой разумеющимся требованием. Тут у нас нет многоядерного процессора и гигабайтов оперативки. В «профессиональном обучении» программиста это где-то год.

Дальше — микроконтроллерная специфика. Да, «входной порог» в программирование для микроконтроллеров сейчас (благодаря все той же ARM mbed) сводится «до уровня базовых знаний C/C++ и электроники в масштабе «подключить светодиод в нужной полярности»» (c) — но для понимания штук типа CMSIS-NN желательно уже иметь представление об архитектуре ARM, всякого рода оптимизациях, DSP-инструкциях (зря что ли мы берем Cortex-M4?) и прочей такой вот низкоуровневой ерунде — возможно, вплоть до программирования на ассемблере. Электроника, нужная для такого проекта, разумеется, тоже довольно далеко ушла от «подключить светодиод в нужной полярности».

В общем, если представить учебники по каждой из дисциплин — тут «вырисовывается» книжная полка с десятком книжек страниц по 300 каждая (это минимум — некоторые особенно «хорошие» учебники по некоторым разделам computer science приближаются к полутора тысячам страниц). Можно, конечно, возразить с аргументами в духе разделения труда — мол, не обязательно специалисту по deep learning знать нюансы архитектуры ARM, да и математика ему не особо нужна, и вместо одного «универсала» тут можно взять трех-четырех выпускников трехмесячных курсов. Но с другой стороны — над ними все равно должен быть какой-то руководитель — который должен иметь представление не только о технических аспектах, но еще и направлять процесс разработки.

И заметьте — все это только для того, чтобы можно было пальчиком провести по тачскрину, а на дисплее отобразилась бы введенная цифра. Но, конечно, всегда есть и более простой путь — «еще три года назад Антон был простым раздолбаем, а сегодня он Senior Developer в Luxoft» (c). Сеньер-формошлепом, наверное, быть неплохо :)

Вот подумалось тут

Разбирая непрочитанные закладки в браузере, наткнулся на «заложенную» статью о Progressive Web Applications. Я некоторое время назад задумался о простеньком веб-приложении, умеющем работать в «оффлайне» — точнее, способном сохранить введенные в форму данные и затем синхронизировать их с сервером, так что краем глаза увидев «рекламу» концепции Progressive Web Application, подумал — это как раз то, что нужно! Вот сегодня наконец-то руки дошли до погуглить, что это такое и как они делаются — и если честно, я немного офигел.

Идея, если подумать — очень простая. Немалая часть «приложений» для Android или iOS — это несложные обертки над каким-нибудь API, работающим поверх обычного HTTP. Некоторые вообще не парятся и отрисовывают весь пользовательский интерфейс в WebView или как он там называется, и даже реализуют «содержательную» часть приложения на браузерном JavaScript. Так вот, зачем плодить такого рода «приложения», если можно сохранить на устройстве «главную страницу» сайта (или «приложения») вместе с необходимым JavaScript и прочими ресурсами (CSS, картинки и так далее)? PWA — это небольшой набор средств, позволяющих добавить специально оформленную веб-страничку в список «приложений» на устройстве с Android или iOS. К этому добавляется возможность зарегистрировать в системе некоторый код на JavaScript для фонового выполнения — эта штука называется ServiceWorker — и готово!

Примерно тот же набор фактов вперемешку с основными принципами разработки «прогрессивных веб-приложений» излагается обычно на паре страниц мелким текстом, засоренных «птичьим языком» про «rich mobile experience», «new level of quality» и тому подобную ерунду. В худшем случае все сводится к этой самой ерунде, а технические детали опускаются совсем.

Вот мне интересно — в других, отличных от веба разделах того, что обычно называют «информационными технологиями», отношение количества вот такого буллшита к техническим деталям обычно немного ниже. А почему?

Мнение нормального человека об этой вашей ардуине

Хочу заметить — пишет не «электронщик» ни разу:

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

https://felixit.blog/2018/10/02/pro-arduino/

О профессиональной этике

Полистал тут книжечку Modern Assembly Language Programming with the ARM Processor by Larry D. Pyeatt, в частности, главу про арифметику с фиксированной запятой. В этой главе упоминается про известный случай с заглючившей системой Patriot, а в одном из упражнений предлагается обсудить это, исходя из положений Software Engineering Code of Ethics And Professional Practice.

Интересно, а многие ли отечественные программисты слышали про такой документ?

Code of Conduct здорового человека

Крайне рекомендую к внедрению в опенсорсных проектах:

https://github.com/unwireddevices/RIOT/blob/loralan-public-2018.07/CODE_OF_CONDUCT.md

UPD Не все понимают, чем он так хорош — смотрите в сравнении с «Code of Conduct курильщика».

Еще кого-нибудь обосру — на очереди TU Darmstadt

Вот я, например, ругаю отечественных доцентов, пытающихся преподавать «информатику» и одновременно хвалю всяких там иностранных Керниганов. Впору заподозрить меня в «низкопоклонстве перед Западом» — но нет, обгадить надо всех ровным слоем. Сегодня под раздачу попадет Технический университет Дармштадта — так получилось, что я добрался до тамошних лекций по Allgemeine Informatik (на русский переводится примерно как «общая информатика»), почитал конспект гуглотранслейтом и ужаснулся.

http://www.ke.tu-darmstadt.de/lehre/archiv/ws0607/ai1/material/

Технический университет Дармштадта — это вам не кот чихнул, а, как подсказывает нам Педивикия, «один из наиболее известных технических университетов, является членом TU 9». Вводный курс по «общей информатике» читает профессор Йоханн Фурнкранц — может, он действительно большой специалист по «искусственному интеллекту», но преподавать не умеет от слова совсем.

Итак, курс «общей информатики» рассчитан на два семестра, читается он бакалаврам и магистрам разных специальностей — как связанных, так и не связанных с программированием. Не будем пока особо вникать в содержание и посмотрим на контрольную работу из второго семестра (гуглотранслейт вам в помощь).

Вопрос первый стоимостью 10 баллов — про память компьютера Commodore C64. Мгновенно отсекает студентов, не слышавших слова типа «шина адреса» и «шина данных» — ну или привыкших думать над вопросом, а не мгновенно переводить все встреченные числа в двоичный вид. Теоретически, ответ на этот вопрос можно найти в лекциях — на 6 слайде лекции про фон-Неймановскую архитектуру немножечко рассказывается о разрядности данных и адреса, но многие ли студенты будут в состоянии это запомнить, понять и применить на экзамене?

Второе задание на 12 баллов проверяет склонность к зубрежке и начетничеству, которую многие преподаватели путают с освоением предмета. Вопрос — «что такое дигитализация и почему это важно для современных компьютеров?» Прилежный студент-отличник должен встать по стойке «смирно» и бодро оттарабанить заученное: «Современные компьютеры — это цифровые компьютеры и вся информация, как то: символы, тексты, изображения, музыка, видео и так далее должна быть преобразована в цифровую форму, то есть представлена последовательностью из нулей и единиц!» Просто прекрасен вопрос о том, является ли Java интерпретируемым или компилируемым языком. Интересно, можно ли на экзамене сказать про JIT-компиляцию, или профессор выпадет в осадок?

Задание третье, 8 баллов — таблицы истинности. Ну тут сложно придумать что-то совсем нехорошее. Единственная претензия с моей стороны — вот такие обозначения для всяких там дизъюнкций и конъюнкций только запутывают. Одна и та же операция может обозначаться аж тремя способами («как в математике», буковками — OR, AND, NOT, и «как в Java» — &&, ||, !) — не многовато ли?

Задание четвертое аж на 15 баллов. Тут начинается «программирование». О том, как оно изучается — надо сказать отдельно. Быть может, и неплохо вводный курс программирования начинать с «робота» типа того, который был в учебнике Кушниренко (вообще, «гонять робота по клетчатой доске» — прекрасный способ продемонстрировать «содержательное» программирование, не прибегая к математике типа метода Ньютона или даже квадратных уравнений), но «немецкий» Karel J. Robot — это что-то чудовищное.

Во-первых — может быть, многие уже забыли, но Си-подобный синтаксис — это полная дикость для человека, видящего его в первый раз. Хуже может быть только какой-нибудь APL (и то не факт). Немецкий «робот» — это довольно тонкая «обертка» над языком Java, соединенная с редкостно уебищной IDE. Вы удивитесь, но у живого человека возникают проблемы с тем, надо или не надо ставить точку с запятой после for(…) или if(…), где ставить и где не ставить какие скобки (их, напомню, в Си и других языках с похожим синтаксисом аж три сорта), ну и так далее. В любом редакторе кода для «кушниренковского» (в широком смысле — отношу сюда и разработанного в 57 школе «Робота«) эта проблема решалась тем, что все конструкции языка программирования вводились через контекстное меню (что-то типа Code Snippets во «взрослых» IDE) — здесь же не умеющих программировать студентов оставляют наедине с ущербным текстовым редактором (кажется, даже без подсветки синтаксиса). Зато полдесятка слайдов в лекции по работе с Karel J. Robot и задание в одной из контрольных посвящены всевозможным «орфографическим» ошибкам — что как бы намекает на основные сложности.

Впрочем — и это будет второй и главной претензией к содержанию курса — он вовсе не рассчитан на «не умеющих программировать». Первый же пример кода в этом курсе появляется во второй лекции (слайд 21). Вы уже знаете, что такое переменная, массив, цикл? Тогда вам остается только покивать головой «Ja, Ja» в ответ на объяснения со следующего слайда. Не знаете? Это ваши проблемы. Я почти не шучу — «программирование» начнется в лекциях по Karel J. Robot и новые понятия будет появляться в бешеном темпе. Прекрасно, если вы что-то слышали про условный оператор и циклы в любом языке программирования. Не слышали? У вас есть три слайда, чтобы разобраться.

Заодно — и это, как я слышал, нередко в немецком «программистском» образовании — в этом курсе очень большое внимание уделяется построению безумных иерархий классов. Я видел выпускника немецкого ВУЗа, считавшего, что он умеет программировать на Java — но все это «программирование» сводилось к написанию кучки классов и интерфейсов. Примером тому может служить и эта задачка.

Столько же баллов «стоит» и задание номер 5 — элементарная задача по работе с массивами. Единственная сложность, видимо — «программирование на бумаге».

Следующие два задания по программированию — снова «робот» (25 баллов) и Java (15 баллов), надо реализовать довольно подробно расписанное «техническое задание». Казалось бы, в оцененной в 25 баллов задаче надо как-то проявить смекалку и креативность? Но нет, там тупейший кодинг, сопряженный с борьбой против убогости «робота».

Что же видим по итогам двух семестров (в техническом университете, хочу заметить)? Проверяемый уровень знаний соответствует примерно российскому ЕГЭ по «информатике», да еще и отягощен бездумным изучением Java. В курсе не разбирается ни одного хоть сколько-то нетривиального алгоритма (видимо, из-за нехватки времени). Да что там говорить, когда в лекции «Что такое методы» примерно половина слайдов уделена вопросу, чем метод класса (то есть с ключевым словом static) отличается от метода объекта!

Теперь — маленькая вишенка на торте. Напомню, что этот курс читается всем специальностям, где предусмотрена «информатика», в частности — магистрам по специальности «компьютерная лингвистика«. Два семестра из четырех отводится на этот лютый онанизм, предназначенный скорее для будущих «профессиональных программистов на Java» — и лишь в третьем семестра ВНЕЗАПНО в программе появляется Python с NLTK. Хочется спросить — а почему бы не начать с того же питона? Но нет, сначала надо вынести мозг при помощи Java, а затем немногим выжившим — показать их настоящий профессиональный инструмент.

UPD Первая лекция третьего семестра у компьютерных лингвистов начинается со сравнения Java и Python в духе «в Java ужас-ужас и непонятно, а в Python все очень легко и просто»:

java-vs-python

Вопрос о целесообразности изучения Java в течение двух первых семестров остается открытым.

Заодно — начинать с Java, говорят, вредно и для будущих программистов. Во всяком случае, мучения джависта, пытающегося осознать «модель RAM» из первой же главы книжки Кормена я как-то наблюдал лично.

Быдлохабр, часть очередная

https://habr.com/post/423889/

В комментариях перепись говнокодеров.

Да, если у вас тормозит (сюрприз, да?) страничка хабра с тысячей комментов — то содержательную часть публикации оттуда можно прочитать у автора (на английском, правда):

http://tonsky.me/blog/disenchantment/

Онлайн-IDE с чятиком

А может, кто-нибудь подскажет такую штуку? Хочется работающий в онлайне «многопользовательский» (ну или «на двоих» — чтобы была возможность обсуждать маленькие, почти тривиальные примеры кода, используя для этого что-то поудобнее вконтактика) редактор и компилятор Java, соединенный с текстовым чатом, желательно бесплатный. Пока что нашел два с половиной сайта с близкой, но немного не устраивающей меня функциональностью.

Первый — https://codeinterview.io, он же https://www.remoteinterview.io. Платный, но для моих задач вроде как подходит и демо-версия. Довольно большой выбор языков программирования, есть unix shell и видеочат. Текстовый чат отсутствует. Платная версия дорогая — 500-1000 $ в год, или 5 $ за каждое «собеседование». Мне кажется, что «для двоих» можно завести одно такое «собеседование», заплатив 5 $ один раз, или же пользоваться бесконечно оформляемым на разные левые email-ы free trial.

Второй — https://codebunk.com, в отличие от предыдущего варианта, для интерпретируемых языков прикручено окошко с REPL, есть текстовый и видеочат. По-моему, демо-режим поддерживает только одного работающего пользователя. Заметно дешевле предыдущего варианта — 9 $ в месяц.

Гугл выдает еще https://coderpad.io/ — опять же, позиционируется, как инструмент для проведения программистских собеседований, есть компилятор и видеочат, стоит от 50 $ в месяц, free trial на 7 дней — но у меня заработало не во всех браузерах.

Что нибудь еще подобное есть?

Чтобы глупость каждого видна была

Вот, например, некий Михаил Плаксин, доцент из пермского филиала ВШЭ кидает понты в фейсбуке:

plaksin

Ну в целом никто его за язык не тянул — так что «уважаемые оппоненты» пошли на сайт ВШЭ в раздел «Преподаватели и сотрудники» и откопали там страничку доцента с его многочисленными работами, частью даже выложенными для скачивания:

https://www.hse.ru/org/persons/4200771#sci

Продираться через всякий ТРИЗ и прочую «ТРИЗформатику» малоинтересно — а вот получить представление, как большие специалисты по преподаванию информатики что-то рассказывают детям, удалось:

https://yadi.sk/i/gWwvY-h3HDKA0Q

Докопаться, конечно, тут можно буквально до всего — от странных представлений автора о точности вычислений до использования в примерах древнего Turbo Pascal — но тут же есть еще один глобальнейший «косяк». Приведена куча примеров «неточных» вычислений — и никоим образом не объясняется, что же происходит «на самом деле» (и вообще — написать обширный текст о машинной арифметике и ни разу не намекнуть на IEEE 754 — нужен талант). Что вынесет из этой статьи читатель? «Компьютер считает не всегда точно, что с этим делать и кто виноват — неизвестно». Неужели именно этого и добивался всеми силами автор?

Understanding the Digital World: What You Need to Know about Computers, the Internet, Privacy, and Security

Оказывается, Брайан Керниган (один из авторов языка программирования C и операционной системы Unix) еще не впал в маразм и недавно (в 2017 году) написал книжку с подзаголовком «что нужно знать о компьютерах, Интернете, приватности и безопасности».

understanding-the-digital-world

Основное содержание книги — что-то вроде конспекта курса лекций по «Введению в Computer Science», или CS 109 в университете Принстона (кстати, очень полезно посмотреть задания и лабораторные по этой ссылке). Примерно 3/4 книги повторяют более раннюю «D is for Digital: What a well-informed person should know about computers and communications», но здесь добавлен новый материал по криптографии, безопасности и тому подобным вопросам.

Если вам интересно, что действительно должно быть в нормальном современном учебнике по «Основам информатики и вычислительной техники» — посмотрите эту книгу и упражнения к ней.

Hadoop против Unix shell

Прикольно как — обработка одного и того же набора данных модными современными инструментами (Amazon EMR и mrjob) занимает 26 минут, а простыми средствами Unix shell — 12 секунд.

https://adamdrake.com/command-line-tools-can-be-235x-faster-than-your-hadoop-cluster.html

«Наивное» решение средствами все той же командной строки обрабатывает те же данные за 70 секунд — что уже вполне терпимо.

Очередное унижение программистов

https://felixit.blog/2018/08/16/elita/

Все так.

PS Что делать, если не хочется получить по морде? Don’t call yourself a programmer.

Ненавижу хохлов

Селюковское самомнение в сочетании с ахромными (по меркам нищей, в целом, Украины) доходами тамошних «айтишников» — термоядерная смесь.

Хуже индусов, честное слово.

fossil

А кто-нибудь в здравом уме (за исключением [info]vitus_wagner) пользовался системой контроля версий fossil?

https://www.fossil-scm.org/

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

А. В. Столяров, «Программирование: введение в профессию»

Посмотрел на свежие «краудфандинговые» книги А. В. Столярова:

http://stolyarov.info/books/programming_intro

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

Можно ли с чисто педагогической точки зрения яростно обличать «стандартизаторов» языков C и C++? Возможно, не все, что они делают — правильно, но стоит ли осуждать в учебнике (!) современные стандарты? Сам автор книги давно ушел из большого секса, но те, кто по этой книге учится сейчас — будут профессионально заниматься программированием через 4-5 лет. Местами есть относительно разумные объяснения, какими возможностями из новых стандартов пользоваться не стоит — но в целом «вместе с водой выплеснули и ребенка», и, скажем, о существовании того же stdint.h вообще не упоминается. Можно ли сейчас считать компетентным программиста на C, не знающего о существовании этого заголовочного файла — вопрос риторический.

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

2018 год

…а люди все еще с удивлением обнаруживают, что внутри ардуины стоит атмега, и что эту атмегу можно программировать на ассемблере:

https://movaxbx.ru/2018/06/05/как-программировать-arduino-на-ассемблере/

Чтобы не забыть

Столкнулся с интересным поведением Linux при попытке изобразить TCP-соединение с помощью «сырых» сокетов (raw sockets), точнее, чего-то на них похожего. Как только на не открытый «явно» (с помощью bind() и listen()) TCP-порт прилетал какой-либо пакет, что-то в составе операционной системы кидало в ответ пакет с флагом RST. Лечится такое поведение двумя способами — можно либо «недосоздать» сокет (вызвать bind(), listen() и не вызывать accept()), либо добавить правило в iptables, не позволяющее отправлять пакеты с RST — что-нибудь в таком роде:

iptables -I OUTPUT -p tcp --tcp-flags RST RST -j DROP

Про беспилотные автомобили

[info]vitus_wagner подкинул ссылку на MIT-овскую статью по модной теме беспилотных автомобилей. Анонс — «В MIT разработали систему, которая позволяет беспилотным автомобилям ездить по сельским дорогам без точной карты» — не очень точно отражает суть работы. Системы типа nVidia DAVE2, довольно простые в реализации (у меня есть даже подборочка материалов по теме) точно так же могут вертеть рулем в нужном направлении, и для своей работы требуют только видеокамеру, смотрящую вперед — данные от GPS и карта там необязательны.

Что отличает эту систему от «нейросетевого» подхода — даже не детерминированность, пусть даже она и приятна (есть несколько публикаций, показывающих, что нейросеть по образцу сделанной в nVidia «сходит с ума» при некоторых манипуляциях с картинкой — вплоть до того, что пытается повернуть совсем в другую сторону, если изменить в картинке на входе всего один пиксель). Внимательно попробуйте осознать описание DAVE2 — эта система определяет угол поворота руля, исходя из картинки, которую видит перед собой «водитель». Но… Посмотрите на эту схему, в том или ином виде присутствующую в любом вводном материале про спортивное или «экстремальное» вождение:

apeks

Три траектории, изображенные здесь — это три разных способа прохождения одного и того же поворота, в той или иной степени «хорошие» (в зависимости, конечно, от прочих факторов). Для наглядности изображена «шпилька» — поворот на 180°, но вся та же теория остается верной и в том случае, если угол будет другим. «Осознанное» управление автомобилем предполагает, что водитель, подъезжая к повороту (из левого нижнего угла картинки), определит точку поворота руля и точку апекса — и, соответственно, траекторию в повороте. Но обратите внимание, что видимая картинка при приближении к повороту во всех трех случаях одинакова — так что система, полагающаяся в своем принятии решений только на текущий видеокадр, очевидно будет неспособна «выбирать» траекторию. Обратите внимание на то, как в ролике nVidia нейросеть «крутит» руль, дергая его туда-сюда (примерно на 7:32):

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

Так вот, важнейшее, на мой взгляд, новшество в подходе MIT — это определение траектории, исходя из конфигурации дороги. Границы дорожного полотна их система определяет с помощью лидара, сканирующего пространство вокруг автомобиля с частотой 5 раз в секунду. Затем строится «локальная» траектория (довольно примитивным, правда, образом — ровно посередине между левой и правой обочинами «вписывается» сплайн, то есть достаточно гладкая кривая), и до очередного обновления автомобиль движется по этой траектории. Никто, в общем, не мешает «вписывать» траекторию и более «правильным» образом — скажем, между правой обочиной и серединой дороги, как предписывают ПДД.

Заметьте, насколько это отличается от подхода «авось нейросеть научится» :)

База данных за один вечер и три бутылки пива

Для начала — о том, как делать не надо. Вот представьте, что вам надо сохранять в какой-нибудь базе данных показания каких-нибудь датчиков, чтобы потом показывать их в модном веб-приложении. Вы уже хотите написать что-то в таком духе?

CREATE TABLE measurements (
    measurementID int NOT NULL AUTO_INCREMENT,
    sensorID int NOT NULL,
    time datetime NOT NULL,
    value double NOT NULL,
    PRIMARY KEY (measurementID)
)

Это очевидно неправильно — имел удовольствие несколько лет подряд наблюдать за эволюцией небольшой SCADA-системы, где хранение данных организовали примерно так. Пока датчиков было немного — оно работало, но примерно на сотне-другой обновляющихся примерно раз в 5-10 секунд датчиков потребовало для работы некоторых костылей. Для начала — в БД перестали записывать «небольшие» изменения данных — скажем, меньше 5% (величина была выбрана довольно произвольно — не надо спрашивать, соответствует ли такой подход требованиям технического задания :) ) от предыдущего сохраненного значения. Затем — по мере накопления данных соорудили чудовищную систему из триггеров и хранимых процедур, которая автоматически создавала «архивные» таблицы сравнительно небольшого размера. Впоследствии, конечно же, выяснилось, что эта система временами глючит и иногда новую таблицу для архива надо создавать вручную.

Наконец, на одном из объектов в дополнение к привычным «медленным» газоанализаторам поставили два десятка акселерометров — и тут все повалилось уже серьезно. Во-первых… нет, для начала в нулевых. Не надо говорить мне, что datetime в SQL неспособен хранить данные с «разрешением» меньше секунды, а опрашиваемый раз в секунду акселерометр бесполезен — тут речь шла уже о том, чтобы записать в базу хоть что-то. А теперь во-первых — показания акселерометров меняются сравнительно быстро и под фильтр «небольших» изменений данных не подпадают, и во-вторых — отказы БД стали чуть ли не ежесуточными. Считайте сами — в сутках 86400 секунд, и при двух десятках пишущих что-то датчиков мы влегкую получаем 1,7 миллиона записей в сутки. Да, часть из них отфильтруется — но и миллиона строк хватит, чтобы популярные СУБД с SQL хорошо и надежно «легли».

Признаться, я списывал многое из этих проблем на невысокую квалификацию разработчиков этой системы, но после доклада Сергея Аксенова “Антипаттерны разработки программных комплексов для интернета вещей” на Inothings++ понял, насколько героические люди используют SQL для хранения такого рода данных. Про выбор СУБД в видео — с 4:28:

Идея понятна — реляционные СУБД расчитаны на количество строк порядка миллионов (десятков миллионов — если у вас поблизости есть грамотный администратор баз данных), а как легко посчитать — это всего лишь суточный архив сравнительно небольшой системы. Впрочем, случай «Стрижа» еще более-менее прост — частота опроса каких-нибудь ЖКХшных счетчиков относительно небольшая, всего несколько раз в сутки. А что делать, если хочется хранить, скажем, данные по 16 каналам АЦП с небольшой в общем-то частотой дискретизации в 16 тысяч выборок в секунду? Нет, я прекрасно представляю, как это сделать «на файлах», и это совсем не сложно — простенький формат хранения данных можно полностью реализовать за неделю неспешной работы (собственно, что-то наподобие edflib, но работающее на микроконтролере с сотней килобайт памяти я написал в прошлом году где-то за несколько дней):

Implementing EDF takes a week. EDF+ takes a few weeks but is better and more powerfull. If you still decide to start with EDF, it is wise to adopt the 12 simple additional EDF+ specs.

Не смотрите, что он предназначен для записи всяких физиологических данных — я в таком виде пробовал всякие обороты двигателя, расход воздуха и прочее время впрыска записывать, они в этот формат прекрасно вписываются :)

Еще из полезного чтения — статья Luca Deri о системе, названной им tsdb — построенной поверх Berkeley DB системе, обеспечивающей хранение миллионов (!) временнЫх рядов (time series — собственно, это общее название для такого рода данных). Решение не совсем подходящее для моего случая — но опять же содержащее несколько полезных идей.

Для начала — система, многократно превосходящая по производительности решения на основе SQL, реализована всего лишь в 1000 или около того строк кода на Си. Именно это и вдохновило меня на написание собственного решения — 1000 строк это совсем немного, а следовательно, должно быть довольно просто. Второе — данные желательно каким-либо образом объединять — если в tsdb это сделано довольно произвольным образом (в базе много редко обновляемых временных рядов), то в моем случае я просто решил писать «секундные» (или соответствующие какой-то доле секунды) записи, как в EDF.

В общем, осознав эти «три источника и три составные части», я взял пивка и засел за Visual Studio — и примерно за вечер написал прототип базы данных, оптимизированной под мои требования — десятки-сотни одновременно записываемых временных рядов с частотой дискретизации от единиц до тысяч Гц. Собственно, по факту получился тот же EDF, только записанный в Berkeley DB. Выбор довольно произвольный (прежде всего — ее используют в tsdb) — но эта, так сказать, «встраиваемая СУБД» поразила меня своей простотой. Немного не радует лицензия — хотя при желании могу выложить код на какой-нибудь гитхаб для очистки совести.

Что могу сказать? Не прилагая никаких усилий в части оптимизации, на собственном ноутбуке я «из коробки» получил скорость записи в базу данных около 40-50 Мбит/с (похоже, упираясь в производительность жесткого диска) — причем, судя по всему, падения производительности с ростом числа записей в БД не происходит. Например, в БД размером около 11,5 Гб — это чуть меньше 1,5 миллионов записей по 8 килобайт (в каждой из записей — по 4000 «точек», каждая из которых — двухбайтовое целое) никакого снижения скорости записи или чтения я не наблюдал (дальше просто стало жалко жесткий диск). Что забавно — тесты «на чтение» демонстрируют полезность кеширования — сначала 10 000 записей читаются за долгие 8 секунд, а затем, если повторить тот же тест «не отходя от кассы» — за 0,22 секунды. Не видел бы — не поверил.

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

PS А если вам все же нравится SQL — почитайте, как правильно организовывать хранение time series в реляционной БД:

https://blog.timescale.com/time-series-data-why-and-how-to-use-a-relational-database-instead-of-nosql-d0cd6975e87c

И все-таки хочу напомнить, что решение «на коленке» практически не уступает приведенному в статье по ссылке в плане производительности (и да, надо бы проверить его с четырехгигабайтным кешем :) ).