range-sum-query-2d
(matrix-block-sum решается подобным образом)
В описании требуется, чтобы метод sumRegion работал за O(1)
Чтобы этого добиться надо использовать префиксные суммы, то есть заранее посчитать суммы блоков.
🪴 Надо считать только те блоки, у которых верхний левый угол соответствует крайнему положению. --> проходимся двумя вложенными циклами и заполняем Map. Для простоты расчета для n-ой позиции нам стоит:
1️⃣ Прибавить предыдущее левое значение из Map (если есть)
2️⃣ Прибавить значение верхней позиции из Map (если есть)
3️⃣ Вычесть значение , которое находится по диагонали влево & вверх (если есть)
Когда у нас есть все почитанные блоки, то мы можем без проблем получить сумму произвольного блока. См. прикрепленную картинку.
Выполняем следующие действия:
🟥 = 💚 - 💙 - 🩷+ 💜
Чтобы получить сумму произвольного красного блока. Из суммы зеленого блока вычитаем две полосы (верхнюю синюю и левую розовую), а затем прибавляем фиолетовый угловой блок.
Это отличный пример, который показывает, что знания синтаксиса языка, а также работы с двумерным массивом будет недостаточно, чтобы решить задачу. Надо предварительно познакомиться с префиксными суммами и концепцией подобных задач(см. картинку)
🐳 Ставь кита, если бы решил эту задачу с двух ног
(matrix-block-sum решается подобным образом)
В описании требуется, чтобы метод sumRegion работал за O(1)
Чтобы этого добиться надо использовать префиксные суммы, то есть заранее посчитать суммы блоков.
🪴 Надо считать только те блоки, у которых верхний левый угол соответствует крайнему положению. --> проходимся двумя вложенными циклами и заполняем Map. Для простоты расчета для n-ой позиции нам стоит:
1️⃣ Прибавить предыдущее левое значение из Map (если есть)
2️⃣ Прибавить значение верхней позиции из Map (если есть)
3️⃣ Вычесть значение , которое находится по диагонали влево & вверх (если есть)
Когда у нас есть все почитанные блоки, то мы можем без проблем получить сумму произвольного блока. См. прикрепленную картинку.
Выполняем следующие действия:
🟥 = 💚 - 💙 - 🩷+ 💜
Чтобы получить сумму произвольного красного блока. Из суммы зеленого блока вычитаем две полосы (верхнюю синюю и левую розовую), а затем прибавляем фиолетовый угловой блок.
Это отличный пример, который показывает, что знания синтаксиса языка, а также работы с двумерным массивом будет недостаточно, чтобы решить задачу. Надо предварительно познакомиться с префиксными суммами и концепцией подобных задач(см. картинку)
🐳 Ставь кита, если бы решил эту задачу с двух ног
Привычки.
"Атомные привычки" - Джеймс Клир - хрестоматийное руководство про то, как внедрять привычки, как появляются плохие в свою очередь и еще много других нюансов.
Хорошие и плохие привычки одинаковы тем, что в краткосрочной перспективе их эффект малозаметен. Собственно поэтому так сложно внедрять полезные привычки и так легко прилипают деструктивные.
Я использую два совета из книги (там их заметно больше).
1️⃣ Трекер привычек.
В какой-то момент осознаешь, что воспоминания искажают действительность. Ты думаешь, что читал эту книгу пару дней назад, а прошло уже пару недель и т.д. Когда вся информация вынесена на внешний носитель - себя уже не обманешь
2️⃣ Привычка должна быть понятна, а не абстрактна.
Мозг должен осознавать, что конкретно нужно сделать под записью "Английский". Это написание предложений, чтение книги, просмотр сериала с субтитрами, разговор на английском... С пресловутой зарядкой - тоже самое. Просто список конкретных упражнений и их количество. В этом случае будет гораздо проще выполнить, чем думать: "Какое упражнение сделать"
"Атомные привычки" - Джеймс Клир - хрестоматийное руководство про то, как внедрять привычки, как появляются плохие в свою очередь и еще много других нюансов.
Хорошие и плохие привычки одинаковы тем, что в краткосрочной перспективе их эффект малозаметен. Собственно поэтому так сложно внедрять полезные привычки и так легко прилипают деструктивные.
Я использую два совета из книги (там их заметно больше).
В какой-то момент осознаешь, что воспоминания искажают действительность. Ты думаешь, что читал эту книгу пару дней назад, а прошло уже пару недель и т.д. Когда вся информация вынесена на внешний носитель - себя уже не обманешь
Мозг должен осознавать, что конкретно нужно сделать под записью "Английский". Это написание предложений, чтение книги, просмотр сериала с субтитрами, разговор на английском... С пресловутой зарядкой - тоже самое. Просто список конкретных упражнений и их количество. В этом случае будет гораздо проще выполнить, чем думать: "Какое упражнение сделать"
Please open Telegram to view this post
VIEW IN TELEGRAM
Где же изучить sql —> здесь
С клиентской стороны важно знать куда обращаться и как это всё отрисовать. Я считаю, что не лишним будет изучить хотя бы базово реляционные базы данных(БД).
Бытует мнение, что БД и работа с ними для frontend'еров не нужны. Но иногда можно очень быстро сделать выборку по данным(аналитика, логи ошибок), поставить нужные условия и построить график. Тем более это всё укладывается в условный SELECT
С клиентской стороны важно знать куда обращаться и как это всё отрисовать. Я считаю, что не лишним будет изучить хотя бы базово реляционные базы данных(БД).
Бытует мнение, что БД и работа с ними для frontend'еров не нужны. Но иногда можно очень быстро сделать выборку по данным(аналитика, логи ошибок), поставить нужные условия и построить график. Тем более это всё укладывается в условный SELECT
EDA
Первое знакомство с EventEmitter'ом было в домашнем задании мини-курса по ООП от Андрея Кобец. Тогда я еще подумал: «Что это за такой рудимент? Наверное, он уже не используется и не пригодится мне в будущем».
Затем я попал в🤟 и на первом проекте он как раз активно использовался. Мне понравился подход реактивной парадигмы программирования. Потом даже непривычно было переходить на другой стиль написания кода.
К чему всё это. Сейчас прохожу курс, где используется Event-Driven Architecture(EDA). И это почти тоже самое концептуально.
В случае обычного EventEmitter'а у нас в экземпляре есть Map c функциями, которые мы вызываем на определенное событие, а в случае с EDA в nest.js вместо обычного js объекта выступает модуль, где вместо локального Map, события публикуются в Redis.
Хорошая статья для первого знакомства с EventEmitter. В данном случае базовые подходы и концепции помогли мне быстро сориентироваться в другом, незнакомом мне, фреймворке.
Первое знакомство с EventEmitter'ом было в домашнем задании мини-курса по ООП от Андрея Кобец. Тогда я еще подумал: «Что это за такой рудимент? Наверное, он уже не используется и не пригодится мне в будущем».
Затем я попал в
К чему всё это. Сейчас прохожу курс, где используется Event-Driven Architecture(EDA). И это почти тоже самое концептуально.
В случае обычного EventEmitter'а у нас в экземпляре есть Map c функциями, которые мы вызываем на определенное событие, а в случае с EDA в nest.js вместо обычного js объекта выступает модуль, где вместо локального Map, события публикуются в Redis.
Хорошая статья для первого знакомства с EventEmitter. В данном случае базовые подходы и концепции помогли мне быстро сориентироваться в другом, незнакомом мне, фреймворке.
Please open Telegram to view this post
VIEW IN TELEGRAM
1310. xor-queries-of-a-subarray
📍 Чтобы решить эту задачу, надо знать, что такое исключающее или (XOR).
В
Дает единицу тогда, когда только один из двух битов равен 1.
🏷️ Небольшая шпаргалка:
0 ^ 0 = 0
0 ^ 1 = 1
1 ^ 0 = 1
1 ^ 1 = 0
Ход решения:
1️⃣ Посчитать префиксные XOR для каждого последующего элемента. Начальный элемент будет равен 0.
2️⃣ Чтобы получить массив answers, надо проделать операцию XOR между двумя значения prefixXOR, притом второе значение берем с индексом + 1.
Пояснения 🪴
📎 arr = [1,3,4,8], queries = [[0,1],[1,2],[0,3],[3,3]]
// 1 = 0001
// 3 = 0011
// 4 = 0100
// 8 = 1000
📎 Массив prefixXOR = [0, 1, 2, 6, 14]
// 0 : 0
// 1 : 0001 -> 1
// 2 : 0011 ^ 0001 = 0010 -> 2
// 3 : 0100 ^ 0010 = 0110 -> 6
// 4 : 1000 ^ 0110 = 1110 -> 14
📎 Массив answers = [2, 7, 14, 8]
// 0 : 00 ^ 10 = 10 -> 2
// 1 : 001 ^ 110 = 111 -> 7
// 2 : 0000 ^ 1110 = 1110 -> 14
// 3 : 0110 ^ 1110 = 1000 -> 9
💡Почему же применение XOR к заранее посчитанным prefixXOR дает нужный результат в диапазоне?
На примере [1, 2]:
prefixXOR для index 1 = 0001 ^ 0 =1
prefixXOR для Index 2 (добавляем + 1, чтобы включить текущий правый конец) = 0001 ^ 0011 ^ 0100 = 6
XOR для диапазона [1, 2] без префиксных XOR: 0011 ^ 0100 = 7.
Таким образом, можно заметить, что всё, что до нужного диапазона, самоуничтожиться. 0001 ^ 0001 = 0.
📍 Чтобы решить эту задачу, надо знать, что такое исключающее или (XOR).
В
javascript операцию XOR между двумя числами выполняет знак ^ .Дает единицу тогда, когда только один из двух битов равен 1.
🏷️ Небольшая шпаргалка:
0 ^ 0 = 0
0 ^ 1 = 1
1 ^ 0 = 1
1 ^ 1 = 0
Ход решения:
1️⃣ Посчитать префиксные XOR для каждого последующего элемента. Начальный элемент будет равен 0.
2️⃣ Чтобы получить массив answers, надо проделать операцию XOR между двумя значения prefixXOR, притом второе значение берем с индексом + 1.
Пояснения 🪴
📎 arr = [1,3,4,8], queries = [[0,1],[1,2],[0,3],[3,3]]
// 1 = 0001
// 3 = 0011
// 4 = 0100
// 8 = 1000
📎 Массив prefixXOR = [0, 1, 2, 6, 14]
// 0 : 0
// 1 : 0001 -> 1
// 2 : 0011 ^ 0001 = 0010 -> 2
// 3 : 0100 ^ 0010 = 0110 -> 6
// 4 : 1000 ^ 0110 = 1110 -> 14
📎 Массив answers = [2, 7, 14, 8]
// 0 : 00 ^ 10 = 10 -> 2
// 1 : 001 ^ 110 = 111 -> 7
// 2 : 0000 ^ 1110 = 1110 -> 14
// 3 : 0110 ^ 1110 = 1000 -> 9
💡Почему же применение XOR к заранее посчитанным prefixXOR дает нужный результат в диапазоне?
На примере [1, 2]:
prefixXOR для index 1 = 0001 ^ 0 =1
prefixXOR для Index 2 (добавляем + 1, чтобы включить текущий правый конец) = 0001 ^ 0011 ^ 0100 = 6
XOR для диапазона [1, 2] без префиксных XOR: 0011 ^ 0100 = 7.
Таким образом, можно заметить, что всё, что до нужного диапазона, самоуничтожиться. 0001 ^ 0001 = 0.
LeetCode
XOR Queries of a Subarray - LeetCode
Can you solve this real interview question? XOR Queries of a Subarray - You are given an array arr of positive integers. You are also given the array queries where queries[i] = [lefti, righti].
For each query i compute the XOR of elements from lefti to righti…
For each query i compute the XOR of elements from lefti to righti…
Оздоровительная физкультура
Как же прекрасна удаленная работа! На первый взгляд минусов совершенно нет: никуда не надо ходить, сидишь себе целый день за компом, пишешь код... Но есть один нюанс.
Превалирующий малоподвижный образ жизни оказывает негативное влияние на здоровье. Есть куча статей и видео на эту тему. Эксперты утверждают, что 2-3 интенсивные тренировки в неделю не исправят ситуацию при сидячем положении в течение 8 часов, а могут даже усугубить.
Нужна двигательная активность во время работы.
Выход — делать каждые 30-40 минут перерыв на приседания.
Почему приседания?
Если кратко, то во время выполнения задействуются самые большие группы мышц, а значит, кровь прогоняется активнее.
Кроме того, приседания необходимы при обычных тренировках, так как нагружено больше мышц. Следовательно, вырабатывается больше тестостерона, что положительно влияет на общий объем мускулатуры и здоровье в целом.
Вернемся к приседаниям во время перерывов. Мозг любит подтасовывать факты, забывать что-то и так далее. Я стараюсь весь контекст выносить из головы, потому что всё в ней не удержишь.
Долго не мог найти удобный формат, чтобы заставить себя приседать в течение дня. Держать в голове — бессмысленно. Вести электронный счетчик — чересчур. Записывать в блокнот — неудобно: записи теряются среди других и нужно проводить арифметические вычисления вручную, либо зачеркивать палочки.
В итоге увидел обычный механический счетчик и понял — это то, что надо. Он лежит на столе, напоминает о здоровье, считает за тебя, а каждый день просто сбрасывается.
P.S. Оптимальная планка для меня — около 100 приседаний за день. Но, возможно, когда-нибудь дойду до рекордов Приседалыча, но это не точно
Как же прекрасна удаленная работа! На первый взгляд минусов совершенно нет: никуда не надо ходить, сидишь себе целый день за компом, пишешь код... Но есть один нюанс.
Превалирующий малоподвижный образ жизни оказывает негативное влияние на здоровье. Есть куча статей и видео на эту тему. Эксперты утверждают, что 2-3 интенсивные тренировки в неделю не исправят ситуацию при сидячем положении в течение 8 часов, а могут даже усугубить.
Нужна двигательная активность во время работы.
Выход — делать каждые 30-40 минут перерыв на приседания.
Почему приседания?
Если кратко, то во время выполнения задействуются самые большие группы мышц, а значит, кровь прогоняется активнее.
Кроме того, приседания необходимы при обычных тренировках, так как нагружено больше мышц. Следовательно, вырабатывается больше тестостерона, что положительно влияет на общий объем мускулатуры и здоровье в целом.
Вернемся к приседаниям во время перерывов. Мозг любит подтасовывать факты, забывать что-то и так далее. Я стараюсь весь контекст выносить из головы, потому что всё в ней не удержишь.
Долго не мог найти удобный формат, чтобы заставить себя приседать в течение дня. Держать в голове — бессмысленно. Вести электронный счетчик — чересчур. Записывать в блокнот — неудобно: записи теряются среди других и нужно проводить арифметические вычисления вручную, либо зачеркивать палочки.
В итоге увидел обычный механический счетчик и понял — это то, что надо. Он лежит на столе, напоминает о здоровье, считает за тебя, а каждый день просто сбрасывается.
P.S. Оптимальная планка для меня — около 100 приседаний за день. Но, возможно, когда-нибудь дойду до рекордов Приседалыча, но это не точно
Как говорит мой закадычный друг: "Курсов много не бывает."
Под конец августа начал проходить курс по node.js и вот прошло 6 модулей длительностью 7 месяцев.
Я преследовал следующие цели:
расширение кругозора, выработку привычки ежедневно учиться, создание места для маневра (fullstack, backend), получение базовых навыков для создания серверов на node.js
Ко всему прочему на курсе ламповая атмосфера и формат мне импонирует(отсутствие видео с объяснениями); общение, задания в текстовом формате, иногда созвоны.
Изучил базово node.js, потом перешел на написание с помощью express, а затем уже на моднейший фреймворк nest.js. В качестве базы данных на протяжении всего курса использовалась Mongo. Также к середине обучения начал применять подход TDD(Test Driven Development). Было неприятно, но один из проектов получилось написать полностью следуя этому подходу. Потрогал немного микросервисы на nest.js. Также было много полезностей, отдельно их не выношу.
Обучение необходимо по двум причинам:
1) Не учишься - отстаешь
2) Отвлечение от рабочей рутины
Делаю небольшой перерыв и продолжаю дальше. Давно ждут курсы от Кобеца.
Под конец августа начал проходить курс по node.js и вот прошло 6 модулей длительностью 7 месяцев.
Я преследовал следующие цели:
расширение кругозора, выработку привычки ежедневно учиться, создание места для маневра (fullstack, backend), получение базовых навыков для создания серверов на node.js
Ко всему прочему на курсе ламповая атмосфера и формат мне импонирует(отсутствие видео с объяснениями); общение, задания в текстовом формате, иногда созвоны.
Изучил базово node.js, потом перешел на написание с помощью express, а затем уже на моднейший фреймворк nest.js. В качестве базы данных на протяжении всего курса использовалась Mongo. Также к середине обучения начал применять подход TDD(Test Driven Development). Было неприятно, но один из проектов получилось написать полностью следуя этому подходу. Потрогал немного микросервисы на nest.js. Также было много полезностей, отдельно их не выношу.
Обучение необходимо по двум причинам:
1) Не учишься - отстаешь
2) Отвлечение от рабочей рутины
Делаю небольшой перерыв и продолжаю дальше. Давно ждут курсы от Кобеца.
Анимации
Анимации работают только для конечных состояний. И тут возникает проблема: как анимировать элемент, у которого высота равна 'auto' и зависит от содержимого, которое заранее неизвестно.
Спойлер:никак с помощью нативного css
Но можно возразить на этот счет: "Уже завезли свойство interpolate-size в css для height: auto".
В таком случае надо использовать caniuse и заметить, что это свойство плохо поддерживается многими браузерами. Такое не используем.
Тут я нашел два выхода:
1) Эмпирический коэффициент, который из начального состояния высоты посчитает конечную.
Получилось плохо. Зависит от многих факторов, всех учесть невозможно и всё равно получается неточно.
2) Отрисовать незаметно элемент в DOM'e в конечном состоянии, зафиксировать высоту и в дальнейшем использовать.
Получить высоту элемента в потоке html страницы можно с помощью offsetHeight. Но это свойство надо всегда применять с осторожностью, так как оно очень ресурсоемкое из-за того что вызывает reflow.
Статья про reflow
Анимации работают только для конечных состояний. И тут возникает проблема: как анимировать элемент, у которого высота равна 'auto' и зависит от содержимого, которое заранее неизвестно.
Спойлер:
Но можно возразить на этот счет: "Уже завезли свойство interpolate-size в css для height: auto".
В таком случае надо использовать caniuse и заметить, что это свойство плохо поддерживается многими браузерами. Такое не используем.
Тут я нашел два выхода:
1) Эмпирический коэффициент, который из начального состояния высоты посчитает конечную.
Получилось плохо. Зависит от многих факторов, всех учесть невозможно и всё равно получается неточно.
2) Отрисовать незаметно элемент в DOM'e в конечном состоянии, зафиксировать высоту и в дальнейшем использовать.
Получить высоту элемента в потоке html страницы можно с помощью offsetHeight. Но это свойство надо всегда применять с осторожностью, так как оно очень ресурсоемкое из-за того что вызывает reflow.
Статья про reflow
O(n)
О-нотация используется для оценки сложности выполнения программы. Это не определенное число. Это функция, которая показывает во сколько раз изменится количество операций при изменении входных данных. Ошибочно полагают, что если О(1), то операция выполняется мгновенно. Эта запись просто говорит о том, что количество операций не зависит от входных данных. Грубо говоря, когда мы берем значение из Map'ы - нет разницы в величине Map'ы. Но при этом компьютер проведет какие-то вычисления и потратит некоторое время, чтобы найти значение.
О(n) - во фронтенде.
Исходные данные: монитор, процессор, абстрактная программа, которая выполняется за О(n^2)
📺 Монитор будет иметь 100 Гц
💻 Процессор будет с тактовой частой 1ГГц (1 000 000 000 Гц)
При каком количестве входных данных мы заметим, что что-то выполняется очень медленно?
Монитор 100 Гц меняет кадр каждые 10мс. То есть, в том случае, если за 10мс компьютер не успеет посчитать новое значение, мы увидим торможение.
За 10мс процессор может сделать 1 000 000 000 / 100 = 10 000 000 операций.
О(n^2) = 10 000 000
n = √ 10 000 000 = 3 162 - число входных данных, до которых не будет заметен лаг на мониторе.
Такая занимательная арифметика на ночь📺
О-нотация используется для оценки сложности выполнения программы. Это не определенное число. Это функция, которая показывает во сколько раз изменится количество операций при изменении входных данных. Ошибочно полагают, что если О(1), то операция выполняется мгновенно. Эта запись просто говорит о том, что количество операций не зависит от входных данных. Грубо говоря, когда мы берем значение из Map'ы - нет разницы в величине Map'ы. Но при этом компьютер проведет какие-то вычисления и потратит некоторое время, чтобы найти значение.
О(n) - во фронтенде.
Исходные данные: монитор, процессор, абстрактная программа, которая выполняется за О(n^2)
📺 Монитор будет иметь 100 Гц
💻 Процессор будет с тактовой частой 1ГГц (1 000 000 000 Гц)
При каком количестве входных данных мы заметим, что что-то выполняется очень медленно?
Монитор 100 Гц меняет кадр каждые 10мс. То есть, в том случае, если за 10мс компьютер не успеет посчитать новое значение, мы увидим торможение.
За 10мс процессор может сделать 1 000 000 000 / 100 = 10 000 000 операций.
О(n^2) = 10 000 000
n = √ 10 000 000 = 3 162 - число входных данных, до которых не будет заметен лаг на мониторе.
Такая занимательная арифметика на ночь
Please open Telegram to view this post
VIEW IN TELEGRAM
Экстраверт или интроверт
Один из плюсов обучения в универе (а их довольно мало) — это возможность встретить выдающихся людей и что-то у них почерпнуть. Мне посчастливилось тренироваться у Баринова В.В. Помимо интересных тренировок, он всегда делился своими мыслями и взглядами на некоторые вещи через призму баскетбола.
Одно из его наставлений заключалось в следующем: «Я могу быть в жизни экстравертом или интровертом — это неважно, но, когда я играю в баскетбол, я полностью экстраверт. Это выражается в том, что я открыт к передачам, активен и всё в таком духе».
Очень классный посыл, и именно поэтому я его запомнил. Более того, эту же мысль можно применить ко многим другим сферам жизни. Например, вам может нравиться досуг интроверта: уединённая обстановка и тишина. Но в работе важно уметь включать экстраверта:
- Спросить о непонятном моменте, который тормозит процесс,
- Обсудить решение,
- Сделать или получить ревью,
- Поделиться знаниями
и так далее.
Разработка в большинстве своём — это про общение и взаимодействие с другими людьми.
Один из плюсов обучения в универе (а их довольно мало) — это возможность встретить выдающихся людей и что-то у них почерпнуть. Мне посчастливилось тренироваться у Баринова В.В. Помимо интересных тренировок, он всегда делился своими мыслями и взглядами на некоторые вещи через призму баскетбола.
Одно из его наставлений заключалось в следующем: «Я могу быть в жизни экстравертом или интровертом — это неважно, но, когда я играю в баскетбол, я полностью экстраверт. Это выражается в том, что я открыт к передачам, активен и всё в таком духе».
Очень классный посыл, и именно поэтому я его запомнил. Более того, эту же мысль можно применить ко многим другим сферам жизни. Например, вам может нравиться досуг интроверта: уединённая обстановка и тишина. Но в работе важно уметь включать экстраверта:
- Спросить о непонятном моменте, который тормозит процесс,
- Обсудить решение,
- Сделать или получить ревью,
- Поделиться знаниями
и так далее.
Разработка в большинстве своём — это про общение и взаимодействие с другими людьми.
Rebase или merge
Много статей написано на эту тему. Если брать в первом приближении merge понятнее и имеет возможность просто откатиться в случае чего.
Rebase, в свою очередь, оставляет историю более линейной, имеет более широкий спектр возможностей, поэтому я нахожусь еще в процессе изучения некоторых моментов данного способа.
Для тех, у кого не так много опыта с rebase, можно перестраховаться так: создавать временную ветку перед rebase'ом или еще одну локальную копию проекта (отнимает много места).
Много статей написано на эту тему. Если брать в первом приближении merge понятнее и имеет возможность просто откатиться в случае чего.
Rebase, в свою очередь, оставляет историю более линейной, имеет более широкий спектр возможностей, поэтому я нахожусь еще в процессе изучения некоторых моментов данного способа.
Для тех, у кого не так много опыта с rebase, можно перестраховаться так: создавать временную ветку перед rebase'ом или еще одну локальную копию проекта (отнимает много места).
Занимательный факт
Недавно узнал интересный факт, с которым сталкиваются все frontend-разработчики.
Код примерно в таком виде писали все. Получаем response, дальше парсим body, чтобы получить json и дальше уже остальная логика.
Но в js есть статический метод JSON.parse и он работает синхронно, а в примере выше асинхронно.
Самый первый промис резолвится тогда, когда мы можем получить заголовки, но body еще может не быть. Если бы промис резолвился относительно получения всего body, тогда метод был бы синхронным, как и привычный JSON.parse. Но это не так.
Знал про это?
🤡 - да 👍 - нет 🌚 - не пишу код
Недавно узнал интересный факт, с которым сталкиваются все frontend-разработчики.
fetch('https://jsonplaceholder.typicode.com/todos/1')
.then(response => response.json())
.then(json => console.log(json))Код примерно в таком виде писали все. Получаем response, дальше парсим body, чтобы получить json и дальше уже остальная логика.
Но в js есть статический метод JSON.parse и он работает синхронно, а в примере выше асинхронно.
Самый первый промис резолвится тогда, когда мы можем получить заголовки, но body еще может не быть. Если бы промис резолвился относительно получения всего body, тогда метод был бы синхронным, как и привычный JSON.parse. Но это не так.
Знал про это?
Please open Telegram to view this post
VIEW IN TELEGRAM
Почти довёл своё рабочее место до идеала: купил нормальное кресло Samurai S-3.05.
Можно работать в разных условиях, но безусловно каждая мелочь влияет на продуктивность и здоровье.
Как в истории с Брейлсфордом и британским велосипедным спортом, где искали варианты улучшений хотя бы на 1 %. Также можно улучшать и рабочее место, пока будет нечего улучшать.
P.S. Хруст в шее — один из симптомов остеохондроза.
Можно работать в разных условиях, но безусловно каждая мелочь влияет на продуктивность и здоровье.
Как в истории с Брейлсфордом и британским велосипедным спортом, где искали варианты улучшений хотя бы на 1 %. Также можно улучшать и рабочее место, пока будет нечего улучшать.
P.S. Хруст в шее — один из симптомов остеохондроза.
Примитивы по значению, а объекты по ссылке
Но это не всегда можно отнести к строкам, ведь строка может занимать довольно много места, а большая часть примитивов не так ресурсоемка.
Сам процесс в ноде занимает около 3,5 мб.
Создаем массив на 5 млн элементов, одна ячейка занимает 8 байт. + 40 мб к занимаемой памяти.
Делаем из массива строку, латинская буква занимает 1 байт. + 5 мб к занимаемой памяти.
Итого получилось 48,5 мб занимаемой памяти. Создаем новую переменную и кладем туда строку. Следуя правилу из названия должны скопировать по значению и увидеть в heapUsed примерно 53,5 мб. Но этого не происходит.
Потому что движок V8 оптимизирует трату памяти в таких случаях.
Но это не всегда можно отнести к строкам, ведь строка может занимать довольно много места, а большая часть примитивов не так ресурсоемка.
Сам процесс в ноде занимает около 3,5 мб.
Создаем массив на 5 млн элементов, одна ячейка занимает 8 байт. + 40 мб к занимаемой памяти.
Делаем из массива строку, латинская буква занимает 1 байт. + 5 мб к занимаемой памяти.
Итого получилось 48,5 мб занимаемой памяти. Создаем новую переменную и кладем туда строку. Следуя правилу из названия должны скопировать по значению и увидеть в heapUsed примерно 53,5 мб. Но этого не происходит.
Потому что движок V8 оптимизирует трату памяти в таких случаях.
const arr = Array(5_000_000).fill("k"); // 5 млн × 8 байт ~ 40 МБ // 43_462_864 байт
const s = arr.join(""); // 5 млн × 1 байт ~ 5 МБ, итого // 48_548_144 байт
const s2 = s;
console.log(process.memoryUsage())Обилие технологий оставляет свой отпечаток: лента негативных новостей, сравнение себя с другими, частое переключение контекста и так далее.
Троица книг, чтобы привести мысли в порядок.
➖ "Тонкое искусство пофигизма" Мэнсон Марк
➖ "Антидот" Оливер Букерман
➖ "Unfu*k Yourself" Гэри Джон Бишоп
Троица книг, чтобы привести мысли в порядок.
Please open Telegram to view this post
VIEW IN TELEGRAM
Недавно попался интересный автор с хорошим слогом, у которого опыт в it около 20 лет.
Очень понравилась статья "Как мы ржавели. История внедрения и обучения". Поймал себя на мысли, что это тот уровень, до которого хочу дорасти. Человек за короткий срок разобрался в новом языке, переписал существующий сервис и уменьшил затрачиваемые ресурсы.
Я решил изучать классический бэкенд в разрезе Java.☕️
При создании javaScript'a опирались на Java, так как он был очень популярен в то время. Поэтому синтаксис javaScript очень схож c Java.
Если был опыт работы с typescript, то переход на Java до уровня написания простых программ пройдет быстро.
Читал про столпы ООП: инкапсуляция, наследование, абстракция и полиморфизм.
Если с первыми тремя всё относительно понятно, то с полиморфизмом поинтереснее.
Я до этого был знаком именно с полиморфизмом подтипов, а видов полиморфизма оказалось больше одного.
В Java есть ad hoc полиморфизм. —> Можно описывать одноименные методы с разными типами. В зависимости от передаваемых типов будет выполнен нужный метод.
Также узнал про параметрический полиморфизм. В typescript это джейнерики.
Очень понравилась статья "Как мы ржавели. История внедрения и обучения". Поймал себя на мысли, что это тот уровень, до которого хочу дорасти. Человек за короткий срок разобрался в новом языке, переписал существующий сервис и уменьшил затрачиваемые ресурсы.
Я решил изучать классический бэкенд в разрезе Java.
При создании javaScript'a опирались на Java, так как он был очень популярен в то время. Поэтому синтаксис javaScript очень схож c Java.
Если был опыт работы с typescript, то переход на Java до уровня написания простых программ пройдет быстро.
Читал про столпы ООП: инкапсуляция, наследование, абстракция и полиморфизм.
Если с первыми тремя всё относительно понятно, то с полиморфизмом поинтереснее.
Я до этого был знаком именно с полиморфизмом подтипов, а видов полиморфизма оказалось больше одного.
В Java есть ad hoc полиморфизм. —> Можно описывать одноименные методы с разными типами. В зависимости от передаваемых типов будет выполнен нужный метод.
Также узнал про параметрический полиморфизм. В typescript это джейнерики.
Please open Telegram to view this post
VIEW IN TELEGRAM
Пишу очередной hello world
Установил всё нужное для компиляции java программ. Скомпилировал файл. Запускаю и получаю ошибку.
Ошибка была связана с тем, что я не снёс старую версию java. Видимо Siemens NX 10 был написан на java 8.
Дело в том, что java - обратно совместимый язык, впрочем как и JavaScript. В этом есть плюсы так и минусы: всё, что попадает в язык, остается там.
Большинство операционных систем(ОС) обратно совместимы. Но так было не всегда, раньше приходилось переписывать софт под новые версии одной ОС. Теперь большинство программ, написанных под старые версии, будут работать в новых версиях одной и той же ОС.
Противоположностью обратной совместимости ставят прямую совместимость. Как пример HTML разметка. Код, написанный с новыми тегами в старом браузере, будет работать (браузер просто пропустит незнакомые теги).
Интересно еще то, что в своей первой книги из серии "You don't know js" Кайл Симпсон в самом начале как раз разбирает два этих понятия.
Установил всё нужное для компиляции java программ. Скомпилировал файл. Запускаю и получаю ошибку.
Ошибка была связана с тем, что я не снёс старую версию java. Видимо Siemens NX 10 был написан на java 8.
Дело в том, что java - обратно совместимый язык, впрочем как и JavaScript. В этом есть плюсы так и минусы: всё, что попадает в язык, остается там.
Большинство операционных систем(ОС) обратно совместимы. Но так было не всегда, раньше приходилось переписывать софт под новые версии одной ОС. Теперь большинство программ, написанных под старые версии, будут работать в новых версиях одной и той же ОС.
Противоположностью обратной совместимости ставят прямую совместимость. Как пример HTML разметка. Код, написанный с новыми тегами в старом браузере, будет работать (браузер просто пропустит незнакомые теги).
Интересно еще то, что в своей первой книги из серии "You don't know js" Кайл Симпсон в самом начале как раз разбирает два этих понятия.
Coderun
Вчера стартанул новый третий сезон Coderun. Рекомендую всем, кому нравится решать задачки. В этом году изменили формат и, как я понял, сделали задачи одинаковые для всех без разделений на домен (фронтенд/бекенд/мл и тд).
Получается не будет зубодробительных задач с css, как эта.
Также вот, например, интересная задача на прототипы в js (по крайней мере я решал ее через прототипы).
Вчера стартанул новый третий сезон Coderun. Рекомендую всем, кому нравится решать задачки. В этом году изменили формат и, как я понял, сделали задачи одинаковые для всех без разделений на домен (фронтенд/бекенд/мл и тд).
Получается не будет зубодробительных задач с css, как эта.
Также вот, например, интересная задача на прототипы в js (по крайней мере я решал ее через прототипы).
CodeRun
Сверстать макет // CodeRun
Задачи для прокачивания навыков разработки фронтенда, бэкенда, мобильных приложений, ML и аналитики. От разработчиков для разработчиков.
В 22:30 будет ссылка на стрим.
Буду пробовать смоделировать шкатулку с ирисовым механизмом. Такое я уже предпринимал пару лет назад, но подгонял всё на лету.
Сейчас появилось желание рассчитать все элементы и сделать нормально. Потом можно написать мини-приложение для расчета разного количества лепестков и заодно поработать с canvas'ом.
Буду пробовать смоделировать шкатулку с ирисовым механизмом. Такое я уже предпринимал пару лет назад, но подгонял всё на лету.
Сейчас появилось желание рассчитать все элементы и сделать нормально. Потом можно написать мини-приложение для расчета разного количества лепестков и заодно поработать с canvas'ом.
Подход к обучению ⚒️
Мне импонирует подход через практику. Если брать программирование, то на начальном этапе — это нарешивание большого количества задач.
Но это время можно провести с еще большей пользой, если к решению задач добавлять написание юнит-тестов.
Также независимо от языка, чаще всего IDE уже предоставляет для этого удобные средства.
Польза очевидная, особенно в эпоху LLM, когда написать код уже не является чем-то сложным.
Архитектурный момент опустим, но для решения локальной задачи остается выбор алгоритма (придумывание решения или выбор из существующих) и верификация результатов.
Нередко бывает, что, вспоминая граничные моменты, дорабатываешь изначальное решение.
4️⃣ случая тестирования, которые следует учитывать:
➖ Пустые, нулевые значения
➖ Граничные значения(максимальное, минимальное)
➖ Регрессионный тест
➖ Множество рандомных тестов
На текущий момент я прорешал довольно-таки огромное количество задач, сейчас приступаю к плотному изучению структур данных. До этого уже было знакомство и прочитана не одна книга. Но читать - одно, а реализовывать и понимать тонкости - совершенно другое.
📔 Грокаем алгоритмы | Бхаргава - великолепно подойдет для первого знакомства
📗 Структуры данных и алгоритмы в Java | Лафоре - отличное объемлющее изложение
📘 JavaScript Algorithms Book | Trekhleb - широкий обзор на алгоритмы и структуры данных через призму JS, есть на гитхабе на разных языках
Мне импонирует подход через практику. Если брать программирование, то на начальном этапе — это нарешивание большого количества задач.
Но это время можно провести с еще большей пользой, если к решению задач добавлять написание юнит-тестов.
Также независимо от языка, чаще всего IDE уже предоставляет для этого удобные средства.
Польза очевидная, особенно в эпоху LLM, когда написать код уже не является чем-то сложным.
Архитектурный момент опустим, но для решения локальной задачи остается выбор алгоритма (придумывание решения или выбор из существующих) и верификация результатов.
Нередко бывает, что, вспоминая граничные моменты, дорабатываешь изначальное решение.
На текущий момент я прорешал довольно-таки огромное количество задач, сейчас приступаю к плотному изучению структур данных. До этого уже было знакомство и прочитана не одна книга. Но читать - одно, а реализовывать и понимать тонкости - совершенно другое.
📔 Грокаем алгоритмы | Бхаргава - великолепно подойдет для первого знакомства
📗 Структуры данных и алгоритмы в Java | Лафоре - отличное объемлющее изложение
📘 JavaScript Algorithms Book | Trekhleb - широкий обзор на алгоритмы и структуры данных через призму JS, есть на гитхабе на разных языках
Please open Telegram to view this post
VIEW IN TELEGRAM