Эффективная загрузка данных в PostgreSQL с помощью Python
В этот раз на курсе ученица столкнулась с задачей загрузки своего датасета в базу данных PostgreSQL. Все бы ничего, это типичная задача, через которую проходят ученики, но здесь повлиял объем исходных данных. На входе был json файл объемом 150Мб, который если преобразовать в формат таблицы, то получится 8.9 млн строк. Не Big Data, но и не маленькая экселька на самом деле.
Мы сравнили разные методы загрузки такого датасета в одну и ту же базу данных в пустые таблицы и вот что получилось:
Самый быстрый метод -
Для COPY предварительно пришлось преобразовать датафрейм в .csv файл, чего например не нужно делать с удобным методом
Кстати, для всех остальных методов вставки которые помню нужно отдельно сначала создать таблицу с помощью
Но часто без
Результаты разных способом по длительности выполнения можете оценить на скрине. 👍 если возьмете себе на заметку
В этот раз на курсе ученица столкнулась с задачей загрузки своего датасета в базу данных PostgreSQL. Все бы ничего, это типичная задача, через которую проходят ученики, но здесь повлиял объем исходных данных. На входе был json файл объемом 150Мб, который если преобразовать в формат таблицы, то получится 8.9 млн строк. Не Big Data, но и не маленькая экселька на самом деле.
Мы сравнили разные методы загрузки такого датасета в одну и ту же базу данных в пустые таблицы и вот что получилось:
Самый быстрый метод -
COPY
(выполнился за 25 секунд). Если вкратце описать его особенность, то этот механизм специально предназначен для массовой вставки данных внутри одного запроса к серверу базы данных, в отличие от INSERT
команды, где каждая вставка будет обрабатываться сервером как отдельный запрос (или группы запросов) и проходить дополнительно разбор sql команды через планировщик базы данных, что также ест ресурсы.Для COPY предварительно пришлось преобразовать датафрейм в .csv файл, чего например не нужно делать с удобным методом
to_sql
. Кстати, для всех остальных методов вставки которые помню нужно отдельно сначала создать таблицу с помощью
CREATE TABLE
, потом уже выполнять вставку. Метод to_sql
сам создает таблицу, если ее в базе данных не существует. Но часто без
INSERT
не обойтись, когда например важно вставлять данные часто и небольшими частями, не сохраняя их при этом предварительно в виде файла. Результаты разных способом по длительности выполнения можете оценить на скрине. 👍 если возьмете себе на заметку
❤28👍19
На днях решал несложную одноразовую задачу по фрилансу. Суть в том, что данные были получены с помощью python и по датасету нужно было сделать несколько преобразований и вычислений метрик.
Преобразования сами по себе стандартные:
Но мне так стало лень писать несколько строк кода на python, что для меня было проще написать всю логику в одном select запросе на sql😁
Вы спросите
Нет, точнее не всегда) Данные остались в том же датафрейме, а обработку я сделал с помощью pandasql.
Простой пример применения и сравнения pandas VS pandasql👇
Я на работе настолько привык крутить все данные с помощью SQL, что в голове любые преобразования я продумываю на логике sql-запросов, а потом если все таки нужно могу переложить это на python скрипты.
Это как с разговорными языками. Если например переезжаете в другую страну и начинаете разговаривать/писать/слушать на другом языке, то у вас мозг со временем начинает мыслить на этом же языке. У меня так было с английским 🇬🇧, когда учеба и работа была полностью на английском, при этом жил в Москве, но все равно замечал что формулирую предложения сначала на английском, а потом уже осознаю что можно на русском)
P.S. sqldf применяет диалект SQLite, поэтому можно использовать все функции которые доступны для этой базы.
👍 если узнали новенькое для себя из поста
Преобразования сами по себе стандартные:
фильтрация
, агрегация
, сортировка
. Можно взять написать все эти операции с помощью pandas к уже имеющемуся датафрейму. Но мне так стало лень писать несколько строк кода на python, что для меня было проще написать всю логику в одном select запросе на sql
Вы спросите
"нафига так делать???" чтобы применить sql данные нужно положить в базу данных
Нет, точнее не всегда) Данные остались в том же датафрейме, а обработку я сделал с помощью pandasql.
Простой пример применения и сравнения pandas VS pandasql
import pandas as pd
from pandasql import sqldf
data = {
'product_id': [1, 2, 1, 3, 2, 3, 1],
'sale_date': ['2023-01-01', '2023-01-02', '2023-01-03', '2023-01-01', '2023-01-02', '2023-01-03', '2023-01-04'],
'amount': [100, 200, 150, 300, 250, 350, 400]
}
df = pd.DataFrame(data)
# логика с pandas (фильтруем по датам, группируем по product_id, считаем агрегат суммы по полю amount и сортируем по нему же)
result_df = (
df[df['sale_date'].between('2023-01-02', '2023-01-03')]
.groupby('product_id', as_index=False)['amount']
.sum()
.sort_values(by='amount', ascending=False)
)
# или применяя sqldf
query = """
SELECT product_id, SUM(amount) as total_amount
FROM df
WHERE sale_date BETWEEN '2023-01-02' AND '2023-01-03'
GROUP BY product_id
ORDER BY total_amount DESC
"""
sql_result = sqldf(query, globals())
Я на работе настолько привык крутить все данные с помощью SQL, что в голове любые преобразования я продумываю на логике sql-запросов, а потом если все таки нужно могу переложить это на python скрипты.
Это как с разговорными языками. Если например переезжаете в другую страну и начинаете разговаривать/писать/слушать на другом языке, то у вас мозг со временем начинает мыслить на этом же языке. У меня так было с английским 🇬🇧, когда учеба и работа была полностью на английском, при этом жил в Москве, но все равно замечал что формулирую предложения сначала на английском, а потом уже осознаю что можно на русском)
P.S. sqldf применяет диалект SQLite, поэтому можно использовать все функции которые доступны для этой базы.
👍 если узнали новенькое для себя из поста
Please open Telegram to view this post
VIEW IN TELEGRAM
👍65❤15
Опыт 🟰 Насмотренность
Каждый понимает, что для ведущего высокооплачиваемого специалиста важно быть опытным. Даже в резюме ключевым фокусом внимания всегда является блок "опыт работы" - что ты уже делал и как решал.
Про опыт
Когда ты джун, каждая задача - это что-то новое, то что ты никогда раньше не делал. В этот момент ты набираешься опыта. Получаешь свой опыт и перенимаешь опыт других коллег, перенимая процесс решения задач, алгоритм анализа, синтаксис скриптов/запросов и т.д., вплоть до привычек решать задачу А с помощью инструмента В, потому что до этого у тебя не было своего опыта и все вокруг тебя делают это так. Ну и ты также начнешь делать.
Опыт заключается в наработке собственных подходов или заимствовании доступных и известных тебе, применяя это здесь и сейчас. Опыт - то что ты приобрел и прошел это.
Про насмотренность
Но я задумался, что опыта на каком-то уровне может не хватать или опыт может быть не совсем правильным/релевантным/эффективным.
Ведь задумайтесь, в одной компании ту самую задачу А все решали инструментом В, а в другой компании эту же задачу А решают другие люди, но инструментами С, D и E. И вполне возможно что твой опыт с вариантом В не самый эффективный, но исходя из опыта ты знаком только с ним и можешь даже не задумываться о том, что есть другое.
Для себя насмотренность я понимаю как "узнать, как решают одну и ту же задачу разными вариантами/подходами/инструментами другие компании/специалисты". Важно понимать, что насмотренность отличается от опыта тем, что ты можешь только посмотреть вариант решения, но не применить его, тем самым не преобразовав это в опыт.
🔎 Насмотренность - знаешь как решать разными способами, опираясь на знания и опыт других, но мог не применять эти знания. Если применил, то получил свой опыт.
🔎 Опыт - прошел путь решения сам или путем заимствования другого опыта.
Мне кажется, что насмотренность более важна для специалистов синьерного уровня, и для этого есть несколько причин:
1️⃣ есть уже наработанный свой опыт и его можно сравнивать с другим опытом через насмотренность. (Типа "я знаю как решить эту задачу и решал ее много раз, но хочу узнать как ее решали другие и сравнить свой опыт)
2️⃣ синьеры как правило являются наставниками для более младших специалистов. и лучше будет сразу в наставничестве давать более широкий опыт: "можно сделать так, а можно иначе, а в другой компании ребята делают так и можешь также попробовать"
3️⃣ опытные специалисты могут быть драйверами роста, внедряя (или пытаясь внедрить) лучшие практики с рынка. а как увидеть эти практики - с помощью насмотренности.
4️⃣ появляется своя команда и часть задач выполняется не твоими руками, а руками твоих коллег. ты можешь повлиять на результат, но не своими руками, а через передачу знаний: "смотри, можем попробовать изобрести велосипед и получить свой опыт, а можем попробовать решить как ребята на конференции рассказывали - посмотрел их решение и предложил тебе попробовать также сделать".
Финализирую:
🔹если джун - нарабатывай собственный и перенимай опыт от своих наставников
🔹если есть базовый опыт - качай насмотренность, как то же самое делают на рынке другие спецы
Каждый понимает, что для ведущего высокооплачиваемого специалиста важно быть опытным. Даже в резюме ключевым фокусом внимания всегда является блок "опыт работы" - что ты уже делал и как решал.
Про опыт
Когда ты джун, каждая задача - это что-то новое, то что ты никогда раньше не делал. В этот момент ты набираешься опыта. Получаешь свой опыт и перенимаешь опыт других коллег, перенимая процесс решения задач, алгоритм анализа, синтаксис скриптов/запросов и т.д., вплоть до привычек решать задачу А с помощью инструмента В, потому что до этого у тебя не было своего опыта и все вокруг тебя делают это так. Ну и ты также начнешь делать.
Опыт заключается в наработке собственных подходов или заимствовании доступных и известных тебе, применяя это здесь и сейчас. Опыт - то что ты приобрел и прошел это.
Про насмотренность
Но я задумался, что опыта на каком-то уровне может не хватать или опыт может быть не совсем правильным/релевантным/эффективным.
Ведь задумайтесь, в одной компании ту самую задачу А все решали инструментом В, а в другой компании эту же задачу А решают другие люди, но инструментами С, D и E. И вполне возможно что твой опыт с вариантом В не самый эффективный, но исходя из опыта ты знаком только с ним и можешь даже не задумываться о том, что есть другое.
Для себя насмотренность я понимаю как "узнать, как решают одну и ту же задачу разными вариантами/подходами/инструментами другие компании/специалисты". Важно понимать, что насмотренность отличается от опыта тем, что ты можешь только посмотреть вариант решения, но не применить его, тем самым не преобразовав это в опыт.
🔎 Насмотренность - знаешь как решать разными способами, опираясь на знания и опыт других, но мог не применять эти знания. Если применил, то получил свой опыт.
🔎 Опыт - прошел путь решения сам или путем заимствования другого опыта.
Мне кажется, что насмотренность более важна для специалистов синьерного уровня, и для этого есть несколько причин:
Финализирую:
🔹если джун - нарабатывай собственный и перенимай опыт от своих наставников
🔹если есть базовый опыт - качай насмотренность, как то же самое делают на рынке другие спецы
Please open Telegram to view this post
VIEW IN TELEGRAM
❤22👍7🔥2
This media is not supported in your browser
VIEW IN TELEGRAM
Уехал в отпуск, в процессе или после поделюсь впечатлениями о поездке длиной в 7+ тыс. км
Собирали вещи 3 вечера, пытался разложить все удобно в машине, но как можете видеть по моему лицу на видео это удалось сделать с трудом 😁
Можете проголосовать за канал, там кажется с 1-го уровня будет доступна 1 история в день. Если наберем 16 голосов, буду делиться с вами красивыми пейзажами Кавказа)
https://t.iss.one/boost/data_study
Собирали вещи 3 вечера, пытался разложить все удобно в машине, но как можете видеть по моему лицу на видео это удалось сделать с трудом 😁
Можете проголосовать за канал, там кажется с 1-го уровня будет доступна 1 история в день. Если наберем 16 голосов, буду делиться с вами красивыми пейзажами Кавказа)
https://t.iss.one/boost/data_study
🔥34❤6
Идеальный вид из окна 😍
P.S. код открыл на ноутбуке чисто для фотки) в отпуске же все таки
Сегодня приехали из Архыза в Домбай. Сходили по маршруту на Сурфуджинский водопад. Здесь заповедная зона, на КПП в заповедник сказали что водопады закрыты из-за сошедшего ледника, поэтому дошли только до «Чертовой Мельницы»
Скину фотку в комментарии оттуда 👇
P.S. код открыл на ноутбуке чисто для фотки) в отпуске же все таки
Сегодня приехали из Архыза в Домбай. Сходили по маршруту на Сурфуджинский водопад. Здесь заповедная зона, на КПП в заповедник сказали что водопады закрыты из-за сошедшего ледника, поэтому дошли только до «Чертовой Мельницы»
Скину фотку в комментарии оттуда 👇
🔥31❤12👍4
🚙 Наш маршрут Road Trip
📍 Архыз
📍 Домбай
📍 Кисловодск
📍 урочище Джилы-Су
📍 Верхняя Балкария
📍 Северная Осетия
Я готовился к путешествию в основном по видео блогеров Своим Ходом, они путешествовали в автодоме по Кавказу в прошлом году. Я так вдохновился местами и красотами, что решил повторить частично маршрут и увидеть все своими глазами.
Расписывал маршрут по дням и времени когда и на какую точку нужно поехать, как передвигаться между локациями и где ночевать.
Топ 3 самых ярких впечатления и локации:
1️⃣ Софийские водопады в Архызе
Голову снесли пейзажи вокруг и сам трекинг до водопадов с кофе-брейком возле них
2️⃣ Домбай
Очумели от высоты и величестве гор вокруг курортного поселка, видом из отеля здесь уже делился. + живописный трекинг и подъем на канатной дороге.
3️⃣ Эльбрус и суслики
Ездили в урочище Джилы-Су с ночевкой. На рассвете нам открылся величественный Эльбрус. Завтрак и кофе на газовой горелке + все утро кормили милых и пугливых сусликов
Помимо этого мы посетили еще большое количество мест, одни переезды от локации к локации приносили уйму эмоций и новые пейзажи за окном.
Возможно вы тоже захотите посетить эти места 😉 Пишите, если захотите спросить что-то более детально
Я готовился к путешествию в основном по видео блогеров Своим Ходом, они путешествовали в автодоме по Кавказу в прошлом году. Я так вдохновился местами и красотами, что решил повторить частично маршрут и увидеть все своими глазами.
Расписывал маршрут по дням и времени когда и на какую точку нужно поехать, как передвигаться между локациями и где ночевать.
Топ 3 самых ярких впечатления и локации:
Голову снесли пейзажи вокруг и сам трекинг до водопадов с кофе-брейком возле них
Очумели от высоты и величестве гор вокруг курортного поселка, видом из отеля здесь уже делился. + живописный трекинг и подъем на канатной дороге.
Ездили в урочище Джилы-Су с ночевкой. На рассвете нам открылся величественный Эльбрус. Завтрак и кофе на газовой горелке + все утро кормили милых и пугливых сусликов
Помимо этого мы посетили еще большое количество мест, одни переезды от локации к локации приносили уйму эмоций и новые пейзажи за окном.
Возможно вы тоже захотите посетить эти места 😉 Пишите, если захотите спросить что-то более детально
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥38👍11❤7
Временные таблицы в базах данных
В ETL процессах часто возникает необходимость в промежуточном хранении данных. Одним из эффективных решений для этой задачи являются временные таблицы.
🔎 Временная таблица — это специальный тип таблицы в базе данных, которая существует только в течение сессии пользователя или до конца транзакции. Она создается для временного хранения данных и автоматически удаляется после завершения работы.
Чем они отличаются от обычных таблиц?
1️⃣ Временность: Временные таблицы существуют только в течение сессии или транзакции, тогда как обычные таблицы сохраняются в базе данных до тех пор, пока их не удалят вручную.
2️⃣ Изоляция: Временные таблицы видны только в пределах текущей сессии или транзакции, что обеспечивает изоляцию данных между разными пользователями или процессами.
3️⃣ Производительность: Временные таблицы часто хранятся в оперативной памяти, что позволяет значительно ускорить операции с данными.
Эти особенности и дают плюсы использования временных таблиц для оптимизации ETL
Пример создания временной таблицы в SQL из результата SELECT запроса:
Также хочу отметить, что временные таблицы позволяют оптимизировать выполнение запросов, если вам нужно преобразовывать и извлекать данные из множества разных таблиц в базе. Например, если из таблицы с продажами за все время вам нужны продажи только за последний месяц для разных видов расчетом, сохраните продажи за последний месяц во временную таблицу и обращайтесь к ней для ваших расчетов, чтобы не делать несколько тяжелых запросов к таблице всех продаж.
В ETL процессах часто возникает необходимость в промежуточном хранении данных. Одним из эффективных решений для этой задачи являются временные таблицы.
🔎 Временная таблица — это специальный тип таблицы в базе данных, которая существует только в течение сессии пользователя или до конца транзакции. Она создается для временного хранения данных и автоматически удаляется после завершения работы.
Чем они отличаются от обычных таблиц?
1️⃣ Временность: Временные таблицы существуют только в течение сессии или транзакции, тогда как обычные таблицы сохраняются в базе данных до тех пор, пока их не удалят вручную.
2️⃣ Изоляция: Временные таблицы видны только в пределах текущей сессии или транзакции, что обеспечивает изоляцию данных между разными пользователями или процессами.
3️⃣ Производительность: Временные таблицы часто хранятся в оперативной памяти, что позволяет значительно ускорить операции с данными.
Эти особенности и дают плюсы использования временных таблиц для оптимизации ETL
Пример создания временной таблицы в SQL из результата SELECT запроса:
CREATE TEMPORARY TABLE temp_table (
id INT,
name VARCHAR(50),
value DECIMAL(10, 2)
);
--либо создание из результата SELECT запроса
CREATE TEMPORARY TABLE temp_table AS
SELECT
id
, name
, value
FROM table
;
Также хочу отметить, что временные таблицы позволяют оптимизировать выполнение запросов, если вам нужно преобразовывать и извлекать данные из множества разных таблиц в базе. Например, если из таблицы с продажами за все время вам нужны продажи только за последний месяц для разных видов расчетом, сохраните продажи за последний месяц во временную таблицу и обращайтесь к ней для ваших расчетов, чтобы не делать несколько тяжелых запросов к таблице всех продаж.
❤20👍9🔥8
Forwarded from Книги по аналитике (BA, DA, SA, PA)
Оптимизация запросов в PostgreSQL / Домбровская Г.
"Книга поможет вам писать запросы, которые выполняются быстро и вовремя доставляют результаты. Вы научитесь смотреть на процесс написания запроса с точки зрения механизма базы данных и начнете думать, как оптимизатор базы данных. Объясняется, как читать и понимать планы выполнения запросов, какие существуют методы воздействия на них с точки зрения оптимизации производительности, и показано, как эти методы используются вместе для создания эффективных приложений."
Скачать книгу
"Книга поможет вам писать запросы, которые выполняются быстро и вовремя доставляют результаты. Вы научитесь смотреть на процесс написания запроса с точки зрения механизма базы данных и начнете думать, как оптимизатор базы данных. Объясняется, как читать и понимать планы выполнения запросов, какие существуют методы воздействия на них с точки зрения оптимизации производительности, и показано, как эти методы используются вместе для создания эффективных приложений."
Скачать книгу
🔥10❤6
Синдром самозванца
Синдром самозванца - психологический синдром, при котором человек не может реально оценить свои качества и личные достижения. Человеку кажется, что он знает меньше других и не достоин того что сейчас имеет. Это проблема адекватной оценки своих достижений и умений.
Лично у себя я ловлю такие мысли иногда, что я "делаю мало", "знаю недостаточно хорошо", "не заслуживаю чего добился" или "мог бы в свои годы достичь большего".
Знакомо❓
Несколько способов как бороться с этим:
1️⃣ Сравнивайте свое текущее состояние с тем что было 1/2/3 года назад
В моменте может показаться, что вы непродуктивны или двигаетесь не так быстро как хотелось бы. Но если вы сравните себя текущего с собой из прошлого, то скорее всего удивитесь как много вы сделали и достигли за это время.
2️⃣ Спрашивайте обратную связь о себе со стороны
Мы себя видим одним образом, люди со стороны могут видеть вас совсем по-другому. Спросите у своих родственников, друзей, коллег что они думают про вас.
- Как бы они вас описали в нескольких предложения, подчеркнув ваши основные черты
- Какие они видят в вас сильные стороны
- Какие они видят в вас недостатки (увы, они есть у всех, но с ними можно работать 👌)
Вы удивитесь сколько нового можно узнать о себе взглядом других людей со стороны.
3️⃣ Всегда занимайтесь саморазвитием и ставьте перед собой цели
Банально, но это дает гарантию, что вы можете оцифровать свои достижения по явному чек-листу прописанных целей. Достижение цели и проставление заветной галочки done ✅ напротив нее дают вам заряд положительных эмоций и фактическое признание своего достижения.
Это пункты, которые я взял себе на вооружение, вы их тоже можете попробовать 😉
Синдром самозванца - психологический синдром, при котором человек не может реально оценить свои качества и личные достижения. Человеку кажется, что он знает меньше других и не достоин того что сейчас имеет. Это проблема адекватной оценки своих достижений и умений.
Лично у себя я ловлю такие мысли иногда, что я "делаю мало", "знаю недостаточно хорошо", "не заслуживаю чего добился" или "мог бы в свои годы достичь большего".
Знакомо❓
Несколько способов как бороться с этим:
1️⃣ Сравнивайте свое текущее состояние с тем что было 1/2/3 года назад
В моменте может показаться, что вы непродуктивны или двигаетесь не так быстро как хотелось бы. Но если вы сравните себя текущего с собой из прошлого, то скорее всего удивитесь как много вы сделали и достигли за это время.
2️⃣ Спрашивайте обратную связь о себе со стороны
Мы себя видим одним образом, люди со стороны могут видеть вас совсем по-другому. Спросите у своих родственников, друзей, коллег что они думают про вас.
- Как бы они вас описали в нескольких предложения, подчеркнув ваши основные черты
- Какие они видят в вас сильные стороны
- Какие они видят в вас недостатки (увы, они есть у всех, но с ними можно работать 👌)
Вы удивитесь сколько нового можно узнать о себе взглядом других людей со стороны.
3️⃣ Всегда занимайтесь саморазвитием и ставьте перед собой цели
Банально, но это дает гарантию, что вы можете оцифровать свои достижения по явному чек-листу прописанных целей. Достижение цели и проставление заветной галочки done ✅ напротив нее дают вам заряд положительных эмоций и фактическое признание своего достижения.
Это пункты, которые я взял себе на вооружение, вы их тоже можете попробовать 😉
👍17❤10🔥4👏2
Делай свои sql запросы слаще!
В языках программирования есть такое понятие как "синтаксический сахар". Это конструкции, которые упрощают написание кода, делают его лаконичным и понятным для разработчика/аналитика. При этом эти синтаксические конструкции преобразуются в более низкоуровневые команды языка для выполнения той функции, которая заложена в конструкцию.
Несколько примеров из SQL👇
CTE (общие табличные выражения) тоже можно отнести к синтаксическому сахару. они реально очень упрощают чтение запросов, но при этом функционал sql позволяет работать и без их использования, обходясь подзапросами.
Можете кстати проверить разные конструкции синтаксического сахара через план запроса и посмотреть во что они преобразуются 😉
Знали про само понятие как "синтаксический сахар" раньше?
👍 - знал
🤓 - узнал сейчас
В языках программирования есть такое понятие как "синтаксический сахар". Это конструкции, которые упрощают написание кода, делают его лаконичным и понятным для разработчика/аналитика. При этом эти синтаксические конструкции преобразуются в более низкоуровневые команды языка для выполнения той функции, которая заложена в конструкцию.
Несколько примеров из SQL
BETWEEN
- конструкция для обозначения диапазона значений вместо конструкции с применением AND и знаков неравенства—синтаксический сахар
WHERE price BETWEEN 10 AND 30
—прямая логика выражения для планировщика запроса будет такая
WHERE price >= 10 AND price <= 30
IN
- конструкция для перечисления множества значений. Но для планировщика это значения с условиям оператора OR—синтаксический сахар
WHERE customer_id IN (5, 7, 12)
—логика для планировщика
WHERE customer_id = 5 OR customer_id = 7 OR customer_id = 12
CTE (общие табличные выражения) тоже можно отнести к синтаксическому сахару. они реально очень упрощают чтение запросов, но при этом функционал sql позволяет работать и без их использования, обходясь подзапросами.
Можете кстати проверить разные конструкции синтаксического сахара через план запроса и посмотреть во что они преобразуются 😉
Знали про само понятие как "синтаксический сахар" раньше?
👍 - знал
🤓 - узнал сейчас
Please open Telegram to view this post
VIEW IN TELEGRAM
👍62🤓33❤8