iOS Dev
7.6K subscribers
970 photos
78 videos
1 file
1.12K links
🍏Канал об iOS-разработке, необычных подходах и решениях.
👨‍💻Автор: Виктор Грушевский (@Viktorianec)
Темы:
⭐️ Подготовка к собеседованиям.
⭐️ Архитектуры и алгоритмы.
⭐️ Код. Много кода.

⚒️База знаний: https://boosty.to/ios_dev

#ios #mobile #swift
加入频道
Декомпозиция задачи или почему добавить одно поле это приключение НЕ на одну минуту?

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

«Вошли и вышли, приключение на 20 минут, Морти!»

К сожалению, зачастую это не так. Особенно если данные для этого поля не хранятся локально.

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

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

При постановке вопроса из примера мы должны перечислить следующие пункты:

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

— Насколько сложно будет изменить структуру в БД? Нужна ли миграция? Тут поможет опыт прошлых апдейтов.

— Нужна ли локализация этого поля? Заглушки, например. Здесь мы видим то, что как и с вопросом про реализацию на сервере не всё зависит от нас.

— Нужна ли валидация этого номера телефона? Нужны ли нам регулярки, может ли номер содержать буквы, например? Сколько может быть символов? Возможно, вы и не удивитесь, но буквы в номерах возможны как минимум в рекламе.

— Какой шрифт, какой цвет, как оформить вообще? Нужна ли анимация при переводе фокуса ввода?

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

В списке выше на самом деле можно выделить сразу два вида декомпозиции:

Вертикальная: сервер, перевод от команды переводчиков, реализация на клиенте.

И горизональная для приложения: подзадача про валидацию, про оформление, про хранение.

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

Декомпозиция нужна, чтобы:

— Понять последовательность выполнения задач.
— Оценить сроки.
— Упростить процесс тестирования.
— Помочь расставить приоритеты. В спринте, но по-хорошему, изначально в бэклоге.

Два небольших вывода:

1️⃣ Мы работаем на бизнес. Поэтому мы должны понимать, почему менеджер может быть недоволен медленной оценкой.

2️⃣ Хочется верить, что этот пост прочтут не только разработчики, но и проект-менеджеры. Профессионалы улыбнутся и скажут, что так и есть. Но те, кто начинает управлять командами — пожалуйста, прочтите этот пост ещё раз.

Специально для @iOS Dev
Архитектура компилятора Swift — что там внутри?

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

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

Ниже приведу высокоуровневое описание основных компонентов компилятора Swift:

Парсинг

Семантический анализ

Импортер Clang

Генерация SIL (Swift Intermediate Language)

SIL-гарантированные преобразования

Оптимизации SIL

Генерация LLVM IR

📖 А вот детальнее про каждый со ссылками и небольшим разбором можно прочесть в моей статье на telegraph.


@iOS Dev — разбираем не только код!
This media is not supported in your browser
VIEW IN TELEGRAM
UIButton с контекстным меню

Контекстные меню встречаются часто и служат неплохим инструментом для взаимодействия пользователя с элементами нашего приложения.

Знали ли вы, что такое меню для кнопки можно добавить буквально несколькими строками?

button.menu = getContextMenu()
button.showsMenuAsPrimaryAction = true


1️⃣ В getContextMenu() нужно вернуть UIMenu.

2️⃣ А с помощью showsMenuAsPrimaryAction мы используем меню как замену обычному действию по кнопке.

Таким образом, UIButton будет действовать как кнопка меню, и вы сможете назначить свои собственные действия.

💡Небольшой совет: если вы будете использовать такой способ, то лучше показать пользователю, что здесь могут быть дополнительные действия. Например, с помощью многоточия (три точки, ellipsis в SF-символах).

@iOS Dev
Руководство для начинающих по массивам в Swift

Хочу сказать всем спасибо за то, что проголосовали в опросе❤️, удивительно много откликов, и это невероятно здорово!
Как обещал, я прочитал все отзывы, сделал себе заметки и даже построил себе план по запрошенным темам.
Одной из просьб, о которых вы просили — побольше материалов для новичков. Что ж, постараюсь насыщать контент канала и материалами для тех, кто только вкатывается в iOS-разработку.

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

📖 А ещё вам может пригодится вот этот материал.

@iOS Dev
This media is not supported in your browser
VIEW IN TELEGRAM
Необычное применение Swift Charts

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

🛠 Код доступен на GitHub.

@iOS Dev
Уровни доступа к сущностям в Swift

⬆️Open — это самый высокий (наименее ограничивающий) уровень доступа.

⬇️ Private — самый низкий (наиболее ограничивающий) уровень доступа.

Всего Swift предоставляет пять различных уровней доступа к сущностям в вашем коде. Эти уровни доступа относятся к исходному файлу, в котором определена сущность, а также к модулю, к которому принадлежит этот исходный файл.

🟢 Open и public позволяют использовать сущности в любом исходном файле определяющего модуля, а также в других файлах с помощью импорта. Обычно open или public используются при указании публичного интерфейса фреймворка.

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

🟡 Internal позволяет использовать сущности в любом исходном файле из определяющего модуля, но не в любом исходном файле вне этого модуля. Обычно internal используется при определении внутренней структуры приложения или фреймворка.

🔴 File-private ограничивает использование сущности только ее определяющим исходным файлом. Используйте доступ file-private, чтобы скрыть детали реализации конкретной части функциональности, когда эти детали используются во всем файле.

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

@iOS Dev
Как появился swipe-to-unlock?
Поделюсь историей появления знаменитого механизма разблокировки.

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

💡 Идея разблокировки телефона пришла в голову Фредди Анзуресу (UI-дизайнеру) не в самом обычном месте. В поисках идей для iPhone он внимательно изучал поведение человека — естественные движения и тенденции, которые можно направить в русло дизайна.

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

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

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

😎 Ах да, ещё один небольшой факт.
Старая запись школьного комбинационного замка, которая сохранилась у Фредди, стала ещё и универсальным звуком разблокировки iPhone.

@iOS Dev — иногда сложные вещи можно решить необычным способом.
Сложности алгоритмов с примерами или что такое нотация Big O?

Детальное описание с примерами в посте ниже.

@iOS Dev
Сложности алгоритмов с примерами или что такое нотация Big O?

Многие из вас о ней слышали, кто-то даже раскладывает за 3 секунды сложность для любого алгоритма, который увидел в первый раз (привет 10x-инженерам), но остальные могут столкнуться c трудностями при оценке. Если вы новичок, Big O может быть одной из первых вещей, с которыми вы столкнётесь при изучении языка.

Цель поста — доступно объяснить, что это такое. Погнали!🚀

🟢 Понятие Big O
Нотация Big O используется для описания производительности функции или алгоритма, применяемого к набору данных, размер которого может быть неизвестен. Это делается с помощью нотации, которая выглядит следующим образом: O(1).

1️⃣ O(1) — эта производительность является лучшей из тех, что можно достичь.
Производительность алгоритма, которая равна O(1), не связана с размером набора данных, к которому он применяется. Поэтому не имеет значения, работаете ли вы с набором данных, содержащим 2, 5 или 1 000 000 элементов. Производительность алгоритма должна оставаться неизменной в любое время.

Пример алгоритма: получение элемента массива по индексу.

2️⃣ O(n) - пример сложности, которая растет по мере роста набора данных .
Эта нотация передает линейный рост. Время выполнения алгоритма или его производительность линейно уменьшается с ростом размера набора данных.

Пример алгоритма: map(), filter() и так далее. Ещё один пример это first(where:).
Если вы думаете, что как же так, first(where:) вернёт первый найденный и производительность точно лучше, чем O(n) — это не совсем так. Нотация предназначена для учёта наихудшего (или наиболее общего) сценария из возможных. Так и в этом примере нужный нам элемент с лёгкостью может быть в конце массива и тогда алгоритм переберёт все элементы.

3️⃣ O(n²) — квадратичная производительность, она характерна для некоторых простых алгоритмов сортировки.

Пример: сортировка пузырьком.

Генерация squareCoords из примера требует, чтобы мы перебирали целые числа с помощью flatMap. В этом flatMap снова цикл по squareCoords, используя map. Это означает, что строка return (i, j) вызывается 25 раз, что равно 5^2. Или, другими словами, n^2. Для каждого элемента, который мы добавляем в массив, время, необходимое для генерации squareCoords, растет экспоненциально. Создание координат для квадрата 6x6 займет 36 циклов и так далее. Уверен, вы понимаете, почему O(n^2) - не самая лучшая производительность.

4️⃣ O(log n) - сложность, которая растет в логарифмическом масштабе.
Алгоритм со сложностью O(log n) часто будет работать хуже, чем некоторые другие алгоритмы для небольшого набора данных. Однако по мере роста набора данных и приближения n к бесконечному числу производительность алгоритма будет снижаться все меньше и меньше.

Пример: бинарный поиск.

Что в итоге?
Big O — это одна из тех вещей, которые нужно часто практиковать, чтобы овладеть ими. Кому-то это даётся проще, кому-то сложнее, но всё приходит с опытом.

Что можно почитать?

📊 Примеры графиков.
📖 Здесь можно увидеть больше примеров.
📖 Cracking the Coding Interview — к этой книге можно относиться по-разному, но вычёркивать её точно не стоит.
📖 Тим Рафгарден: Совершенный алгоритм. Основы.
🛠 Примеры кода и графиков в Swift Algorithm Club на Github.

@iOS Dev
Пять стоп-слов для вашего iOS-приложения

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

Вы можете использовать различные уровни оптимизации для различных конфигураций сборки:

1️⃣ -Onone. Предназначен для обычной разработки. Он выполняет минимальную оптимизацию и сохраняет всю отладочную информацию.

2️⃣ -O. Компилятор выполняет агрессивную оптимизацию, которая может радикально изменить и тип, и количество выпускаемого кода. Отладочная информация будет передаваться, но с потерями.

3️⃣ -Osize. Это специальный режим оптимизации, в котором компилятор отдает приоритет размеру кода, а не производительности.

Чтобы изменить уровень оптимизации, можно перейти в Build Settings -> Optimization Level.

Нам доступно пять вариантов остановки приложения, кроме exit() и abort().

assert.
assertionFailure.
precondition.
preconditionFailure.
fatalError.

📖 Детально каждый из способов описал в статье на telegraph.

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

@iOS Dev
Сохранение паролей c использованием Keychain в Swift

Keychain — это место для безопасного хранения небольших объемов данных, таких как пароли и API-токены. Полезно знать, как работать с Keychain в приложениях для iOS и Mac с помощью фреймворка Keychain Services.

Существует четыре общих действия для элементов связки ключей: добавление, обновление, чтение и удаление. Чтобы любое из них, нужно создать запрос и запустить функцию Keychain Services.

📖 В этой статье автор уделил внимание паролям, которые использует большинство приложений.

@iOS Dev
iOS-интервью: вопросы и ответы для Senior-разработчика на техническом собеседовании

Непростая задача — оценить навыки и знания другого разработчика. В серии постов автор делится своей подборкой вопросов и ответов по iOS и Swift.

Вопросы сгруппированы по темам для большего удобства.

1️⃣ Swift. Цель вопросов для интервью в этой части - узнать общие знания разработчиков о концепциях языка программирования. А также проверить их конкретные знания по Swift.

2️⃣ Networking. Нужно, чтобы узнать общие знания разработчиков о сетевых концепциях и проверить их конкретные знания о сетях в iOS.

3️⃣ Persistence. Для того, чтобы выяснить общие знания разработчиков о концепциях баз данных. А также проверить их конкретные знания в этой области для iOS.

4️⃣ Concurrency. В этой части рассматриваются вопросы и ответы по многопоточности.

5️⃣ Architecture & Design Patterns. В этом разделе рассматриваются вопросы, чтобы познакомиться со знаниями разработчиков об архитектуре и шаблонах проектирования с упором на разработку под iOS.

6️⃣ Testing. Для проверки знаний разработчиков по тестированию приложений с акцентом на разработку iOS.

📖 Кстати, выкладывал раньше материал для собеседований, который тоже может пригодиться.

😃 iOS Dev🐱 Доступ к необычным эффектам
Please open Telegram to view this post
VIEW IN TELEGRAM
Как изменить status bar в симуляторе с помощью терминала?

Это может быть полезно при подготовке скриншотов для App Store или других маркетинговых материалов.

Возможно, вы знаете, что Apple всегда показывает 9:41 на всех своих скриншотах, когда видны часы — это потому, что первый iPhone был впервые показан миру именно в это время.

😉 Сделал сводный материал со списком команд и возможными параметрами, который может пригодиться.

Пример использования:

xcrun simctl status_bar booted override --time 09:46 --cellularBars 3 --dataNetwork LTE --wifiMode failed

@iOS Dev
CoreText в Swift в трёх частях: от HelloWorld к Typesetter
Вы когда-нибудь хотели создать компонент редактирования текста с нуля?

📖 Core Text предоставляет низкоуровневый программный интерфейс для компоновки текста и работы со шрифтами.

Механизм верстки Core Text разработан для обеспечения высокой производительности, простоты использования и тесной интеграции с Core Foundation. API обеспечивает высококачественный набор текста, включая преобразование символов в глифы, лигатуры, кернинг и так далее. Дополнительная технология шрифтов Core Text обеспечивает автоматическую замену шрифтов (каскадирование), дескрипторы и коллекции шрифтов, легкий доступ к метрикам шрифтов и данным глифов, а также многие другие возможности.

В серии статей рассматриваются его аспекты:

1️⃣ HelloWorld c использованием CoreText.

2️⃣ Font Descriptor, Font Metrics, Line height и не только разбираются в этой части.

3️⃣ Верстка текста — нетривиальная задача. CoreText предоставляет несколько полезных функций для отрисовки текста в прямоугольной рамке или вдоль заданного пути. И об этом пойдет речь в третьей части.

@iOS Dev
Как переместить фокус ввода, если у вас открыто два и более редактора?

Используйте CMD+J, а затем стрелки и Enter для подтверждения выбора.

#xcode #shortcuts

@iOS Dev
Конкурсные приложения для Swift Student Challenge

Apple поддерживает студентов по всему миру, которые любят программировать, с помощью захватывающего конкурса Swift Student Challenge.

На конкурсе нужно продемонстрировать свою страсть к программированию, создав проект приложения Swift Playgrounds на выбранную тему.

Победители получают мерч #WWDC, индивидуальный набор значков и годовое членство в Apple Developer Program.

🛠 Подготовил для вас список репозиториев со всеми работами участников за прошедшие годы.

🔗 2022
🔗 2021
🔗 2020
🔗 2019
🔗 2018
🔗 2017
🔗 2016
🔗 2015
🔗 2014

@iOS Dev