Кружка душой из СССР

Новая кружка (78.00КиБ)
Похожие кружки лежали дном вверх в каждой деревне СССР на крышке ведра с ключевой водой

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

Кружка тёплая, лаповая, вызывающая улыбку. От той, что родом из СССР, отличает металл — что-то лёгкое, кажется алюминий, поэтому нагревается моментально, есть такой недостаток, а ещё наверное и мнётся отлично, так что в поход я бы её брать не стал, но главное она у меня не разобьётся.
4 комментария
15 августа 2017 09:57

Что-то не вижу — быть или не быть?

Программа, выводящая монолог Гамлета (19.86КиБ)
Так выглядит программа, выводящая монолог Гамлета

Слово «выглядит» в подписи ко скриншоту выше упомянуто неслучайно — программа написана так, что видимое — только надводная часть айсберга.

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

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

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

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

Что такое суррогатные пары расписывать не буду, статей на эту тему предостаточно, главное, что их не видно и они могу быть частью (кроме первого символа) любого идентификатора ДжаваСкрипта.

Я попробовал использовать способ с суррогатными парами, чтобы скрыть монолог Гамлета внутри программы на ДжеЭсФаке (способ написания программ на ДжаваСкрипте, когда не используются алфавитно-цифровые знаки), плюс этими же парами закодировал имена переменных.

Получилась адская обфускация, глядя на которую и не заподозришь, что она после запуска выведет в консоль полтора килобайта английского текста.
13 комментариев
13 августа 2017 21:48

F★ckJS на поло

Поло со значками (110.09КиБ)
Поло с программой на ДжаваСкрипте, написанной четыре года назад

Очень в тему к предыдущему посту на работе нашёлся мешок с поло размера XXL (из-за размера и сохранился, остальные разобрали).

На поло программа на ДжаваСкрипте, которую я писал к какому-то событию, должно быть готовились к какой-то конфереции — если её запустить в консоли браузера, появляется надпись «prihodite rabotat 88002005221». У меня в «исходящих» сохранилось письмо от 11 марта 2013 года, где я высылаю оригинал этой программы нашему дизайнеру, четыре года уже прошло, надо же.
2 комментария
8 августа 2017 09:11

Bashfuck-3

Hello world (69.01КиБ)
Очередной «Хеллоу ворлд» на «башфаке» — способе программирования на «баше» без алфавитно-цифровых символов

Вчера весь день болела голова и я, чтобы хоть как-то отвлечься, написал, на ночь глядя, ещё один «Хеллоу ворлд» на «баше» в стиле «Башфак» — три года назад эти увлёкся, тогда остались кое-какие нереализованные идеи.

Цель, напомню, написать программу, которая делает что-то разумное, не используя буквы и цифры.

В свежем варианте самое главное новшевство — использование функций.

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

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

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

Имя этой команды легко получается из конструкции перенаправления ввода-вывода в специальный файла вида /dev/fd/XX. Получаем имя этого файла, берём буквы «f», «d» и запускаем полученную команду.

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

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

Из всего вышеописанного получились все буквы, кроме «r» и «w». Первую я получил, запустив на выполнение ls /bin/?m — по маске гарантированно находится файл команды удаления /bin/rm, её имя содержит искомую букву.

Для получения второй воспользовался командой «tr» и идеей, похожей на реализацию ROT13 на «баше» — подобрал диапазоны из имеющихся в моём распоряжении букв так, чтобы одна подходящая буква сдвинулась нужным мне образом — стала буквой «w».
1 комментарий
5 августа 2017 22:18

Небольшие новости по всяким программистким мелочам

Принятый коммит (71.85КиБ)
Коммит, принятый в репозиторий модуля для работы с сервером очередей из ПХП

В прошлом месяце я писал о неочевидных проблемах строгой типизации в ПХП, суть в том, что при её включении немного неудобно поменялась проверка типов входных параметров у внешнего модуля для работы с «Гиэрменом» (Gearman) — сервером очередей. Я сделал крошечный патч, который это исправляет, сегодня ночью его приняли.

Кроме того, мой погодный плагин для «Саблайма» приняли в официальный репозиторий, теперь его можно поставить одной командой.
2 комментария
5 августа 2017 10:35

«Жизнь» Конвея на «R»

«Жизнь» (18.72КиБ)
Одно поколение в игре «Жизнь», запущенной в терминале

Игра «Жизнь» знакома, наверное, каждому программисту. Интересна она тем, что этот незатейливый алгоритм оказал существенное влияние на целый ряд научных дисциплин.

Не помню, чтобы я её когда-то либо программировал в чистом виде, но совершенно точно должен был ею вдохновляться, когда в детстве, ещё на Турбо Паскале реализовывал какую-то собственную её версию с генетическим обменом между соседями.

Сегодня ночью постарался написать классическую версию игры «Жизнь» на языке «Эр». Мне показалось это интересной задачей, так как «Эр» очень удобным образом позволяет работать со множествами так, как будто это скалярные значения.

Это можно увидеть почти сразу, в строке, где создаётся матрица случайных значений:
life <<- matrix(as.integer(runif(rows * cols) < ratio), rows, cols)
Сравнение с переменной ratio и вызов as.integer тут применяется к каждому значению из множества, генерируемого функцией runif (Random Uniform Distribution, генерирует случайные значения с нормальным распределением). Так матрица игры заполняется случайными нулями и единицами.

Ниже по коду довольно много манипуляций с этой матрицей и выполнение правил алгоритма за счёт конструкций языка занимает всего несколько строк.

Суть такова: матрица двигается во все восемь направлений (с шагом 45°), все получившиеся матрицы складываются, это позволяет оценить количество соседей любой клетки в каждом из направлений. Далее в две строки выполняются основные условия:
# Any dead cell with exactly three live neighbours becomes a live cell
life.new[life == 0 & life.neighbors == 3] <- 1
# Any live cell with fewer than two or more than three live neighbours dies
life.new[life == 1 & (life.neighbors < 2 | life.neighbors > 3)] <- 0
Тут участвуют три матрицы: life — поле игры на предыдущем шаге, life.new — поле игры на текущем шаге и life.neighbors — матрица соседей (точка в «Эре» не имеет специального значения). Как видите матрица сравнивается с числом, как будто она скаляр, результат этой операции тоже матрица, но из булевых значений, в каждой клетке — результат операции. Такую матрицу можно использовать как индекс, в результате чего вернутся только те ячейки, по адресам которых в булевой матрице было TRUE.

Дальше просто, поскольку ячейки возвращаются по ссылке, им скопом присваивается требуемое значение.
Комментировать
2 августа 2017 10:00

SELECT [DEFER] * FROM…

Я тут подумал, что было бы очень круто как помечать запросы флагом, который бы говорил СУБД «если такой же запрос уже выполняется, то меня устроят его результаты, новый запускать не надо». Было бы очень полезно для запросов, в которых не нужна оперативность и которые заказываются большим числом пользователей.

Конечно такое можно кешировать со стороны приложения (что у нас и делается в продукте), но встают вопросы инвалидации кеша, предотвращения одновременного выполнения одного и того же запроса несколько раз, если в кеше что-то не нашлось, обработки ошибок от базы и так далее.

Со стороны СУБД было бы интереснее такое увидеть.
9 комментариев
1 августа 2017 17:18

Диета

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

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

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

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

Не знаю на всю это жизнь или на какое-то время, но в принципе меня не пугает так питаться и всё отведённое мне время.
13 комментариев
29 июля 2017 15:08

ПХП и строгая типизация

В ПХП много странностей, ещё одна дала о себе знать в неожиданном месте. Сначала немного теории.

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

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

Последнее очень полезно для числовых и булевых типов — если «нулабельность» не указана, то null будет преобразован по правилам языка в значение указанного типа.

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

Например, у нас преспокойно работал примерно такой код:
    public function put(Serialized $object, $eventName, $extraEventData, $uniqueId = null)
    {
        return DI::gearman_client()->doBackground(
            $this->queueName,
            igbinary_serialize(
                [
                    'object' => $object,
                    'event_data' => $extraEventData,
                    'event_name' => $eventName,
                ]
            ),
            $uniqueId
        );
    }
Всё работало корректно, пока не пришёл ПХП7 и мы не стали потихоньку переползать на строгую типизацию. Вечером я закоммитил изменения в этом файле, которые позволили включить строгую типизацию, а за завтраком поймал в логах странную ошибку, которая сообщала мне, что в метод doBackground время от времени получает в качестве последнего параметра null, а так нельзя.

Сначала я недоумевал, а потом догадался, что случилось — у doBackground последний, необязательный парамер имеет тип «строка» и он не «нулабельный». То есть в строгой типизации я его должен либо не передавать вовсе, либо передавать туда исключительно строку. А null, который передавался туда до перехода на строгую типизацию более не подходит, ибо он не строка.

Пришлось переписать более уродливо:
    public function put(Serialized $object, string $eventName, $extraEventData, string $uniqueId = null)
    {
        $args = [
            $this->queueName,
            igbinary_serialize(
                [
                    'object' => $object,
                    'event_data' => $extraEventData,
                    'event_name' => $eventName,
                ]
            ),
        ];

        if ($uniqueId !== null) {
            $args[] = $uniqueId;
        }

        return DI::gearman_client()->doBackground(...$args);
    }
Странно то, что у необязательного параметра нет никакого значения по-умолчанию, которое можно было бы указать. В принципе, даже если бы оно было, это тоже не очень удобно.

Не смог найти, но я помню, что было чьё-то предложение расширить синтаксис ПХП — разрешить при вызове функции или метода использовать ключевое слово «default» для указания, что в данном месте нужно использовать значение по-умолчанию. Мне кажется тут бы оно пригодилось.
7 комментариев
25 июля 2017 22:18

«Песня о пиве»: R

Как многие наверное помнят, в качестве хобби я время от времени пишу на разных языках программирования американскую «Песню о пиве»

Это довольно известное развлечение — реализовывать на куче языков что-то простое, обычно выбирают числа Фибоначчи, «Песню» или ещё что-то незатейливое.

Я выбрал именно «Песню о пиве», так как не всем языкам из моего списка, под силу что-то большее. До сегодняшнего дня в списке было 57 языков, сегодня, 58-м пунктом, к ним вполне ожидаемо присоединится язык «Эр», о нём я уже немного писал, собираюсь писать и дальше как время образуется.
# Written by Evgeny Stepanischev, 2017

bottles <- function(beer) {
	ifelse(beer == 0, "no bottles",
		ifelse(beer > 1, paste(beer, "bottles"),  "1 bottle")
	)
}

for (i in 99:1) {
	paste(bottles(i), "of beer") -> b

	cat(b, " on the wall, ", b, ".\n", sep = "")
	cat("Take one down and pass it around,", bottles(i - 1), "of beer on the wall.\n\n")
}

cat("No more bottles of beer on the wall, no more bottles of beer.\n")
cat("Go to the store and buy some more, 99 bottles of beer on the wall.\n")
1 комментарий
21 июля 2017 20:37

Читабельный и паркинг

Читабельный (88.37КиБ)
Употребление слова «читабельный» в книге «Дар слова» 1909 года

Признаться, я считал, что слова «читабельный» и «паркинг» очень недавнее изобретение. Я всегда поправляю своих собеседников, если они их употребляют. Мне представлялось, что это приобретение времён Перестройки — когда в страну устремился поток товаров без перевода на русский язык, а с ними и новые слова. Паркинг (63.01КиБ)
Слово «паркинг» в энциклопедии «Великий вызов» 1969 года

Каково же было моё удивление, когда я обнаружил, что слово «читабельный» употребляется в книге «Дар слова» Н. Абрамова, 1909 года выпуска, а слово «паркинг» — в сравнительной энциклопедии США-СССР, «Великий вызов» 1969 года выпуска.

Мне по-прежнему не очевидна необходимость нахождения слова «паркинг» (когда уже есть «парковка» и «стоянка») в языке, а с «читабельностью» я уже кажется готов смириться.
11 комментариев
19 июля 2017 17:24

Ещё находки на газонах

Находки на газонах (95.60КиБ)
Совокупные находки на газонах за последнее время

Проливные дожди, которые не прекращаются с самой весны, портят мне настроение — за летом приходится буквально гоняться, выясняя по карте осадков где сегодня на территории Татарстана не будет дождя. Но польза от них тоже имеется — на газонах, как оказалось, дождь выбивает любопытные артефакты.

Находки с прошлого раза: советская армейская пуговица 1979 года (на обороте надпись — «МОСШТАПМ 79»), бутылёк из-под туши фабрики «Красный художник» (1934—1946 гг.), снизу надпись «СОЮЗ», атрибутировать удалось по части уцелевшей этикетке: «МОСХИМТ[РЕСТ] [Н.] К. [М. П.]», бутылёк советского периода (внизу только цифра — «30»), ¹⁄₂ копейки серебром Николая I (1839—1848 гг., на снимке её нет, забыл положить), 10 копеек 1943, 1 копейка 1949 и россыпь шахтёрских пуговиц.

Бутылочка (68.28КиБ)
Очень красивая бутылочка, лежавшая донышком вверх

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

Пульс покоя в часах

Пуль покоя (33.23КиБ)
График пульса покоя за последний месяц

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

Вообще динамика меня радует — среднее значение за пару лет упало на десять пунктов, а минимум у меня теперь — 60, грех жаловаться. Я, правда, хотел бы ниже, но чёртово лето не радует велосипедной погодой, а в спортзале крутить педали уныло, остаётся надеяться, что занятия с тренером в числе других мышц положительно сказываются и на сердечной.

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

Немного непонятно. Пульс покоя на сегодня у меня 66. Вроде как часы должны мерять пульс сразу перед пробуждением или что-то такое. Но если в момент пробуждения он был 56, то перед пробуждением он должен быть ниже. Я знаю, что наручные часы точностью в измерении пульса похвастаться не могут, но тут речь об обрабоке своих собственных данных. Мне бы хотелось, что бы они хотя бы тенденцию улавливали верно, будет обидно, если они и этого не умеют.
2 комментария
7 июля 2017 09:41

Вызов C из R

Заинтересовался темой вызова функций Си из языка «Эр». Обнаружилось целых два интерфейса: простоватый вызов «.C» и более сложный «.Call», к сожалению ни один из них не предназначен для вызова произвольного кода — со стороны Си в каждом из случаев следует соблюдать некоторые соглашения.

Я решил попробовать подёргать функции библиотеки libmagic, поскольку когда-то делал то же на «Пайтоне». Интерфейс .Call для этой задачи — пушка по воробьям, его имеет смысл использовать, если языки должны обмениваться специфичными для «Эра» структурами, а у меня из типов только строки и числа.

Так как .C не умеет работать с возвращаемыми из функции значениями (возможен возврат только через параметр), да и передаётся всё как указатели, пришлось даже для этой простой задачи написать обёртку. Скомпилировать её можно командой make, либо запустить руками строчку компиляции из файла сборщика.

Программа на «Эре» небольшая, бо́льшую часть занимает определение констант. Внутри захардкожен пример использования, так как библиотеку я делать не намерен, он там так и останется.

Примечание: я знаю, что функция strdup не является переносимой, но мне, если честно, всё равно, не хочется ради исследования принципа тащить в код её реализацию.
Комментировать
1 июля 2017 21:21

Находки на газонах

Найденное (47.47КиБ)
Находки на газонах и на огородике моих хороших знакомых

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

Но это было отступление. Тема внимательного осмотра газонов принесла ещё плоды — 2 копейки 1936, 20 копеек 1956, апекарский пузырёк с надписью «Вильна 30» (так назывался Вильнюс до 1918 года) и гильзу от винтовки Мосина, я её сильно протравил, чтобы посмотреть год, но разглядел только цифру «17», неясно что это — то ли 1917 год, то ли маркировка Подольского завода.

А ещё мои хорошие знакомые позвали меня покапаться на их огородике, прямо после работы, благо от работы к ним ехать недалеко. У них я нашёл 2 копейки серебром 1839—48 гг. и совершенно стёртый медяк, по диаметру аккуратно совпадающий с копейкой Александра III или Николая II. На медяшке уже ничего не разглядеть, а 2 копейки я попробую потравить, может проступят ещё детали.
1 комментарий
29 июня 2017 18:26