Understanding task cancellation and lifetimes in Swift concurrency
ℹ️ В Swift
➡️ Несструктурированные задачи, созданные с помощью
➡️ При работе с долгоживущими задачами, такими как
⚠️ Отмена задач в Swift не останавливает их немедленно, а устанавливает флаг отмены, который асинхронные операции могут проверять для корректного завершения.
structured concurrency связывает время жизни асинхронной работы с областью, в которой она была создана, автоматически отменяя задачи при завершении этой области.Task { ... }, работают независимо и требуют ручной отмены, в то время как Task.detached выполняется полностью независимо от контекста вызова.AsyncStream, важно управлять временем жизни задачи, чтобы избежать бесконечного выполнения.Please open Telegram to view this post
VIEW IN TELEGRAM
👍4
Combine – швейцарский нож iOS-разработчика. Или нет?
ℹ️
⚙️ Основные компоненты Combine включают
➡️
⚠️ Важно помнить о сохранении подписок, так как их отсутствие может привести к потере данных, а также учитывать, что
❓ А вы пользуетесь
Combine — это фреймворк для работы с асинхронными событиями в декларативном стиле, который упрощает управление потоками данных и избавляет от сложностей, связанных с колбэками.Publisher, Subscriber и Subscription, которые взаимодействуют для передачи и обработки данных.Combine активно используется в SwiftUI через аннотации @Published и @ObservedObject, что позволяет автоматически обновлять интерфейс при изменении данных.@Published не сравнивает значения, что может вызвать лишние обновления.Combine?Please open Telegram to view this post
VIEW IN TELEGRAM
👍8👎2
A deep dive into Collections, Sequences, and Iterators in Swift
⚙️
🔼
ℹ️ Цикл
💡
❗️ Создание собственных коллекций требует внимательности к индексам и производительности, чтобы гарантировать, что они соответствуют ожиданиям стандартной библиотеки.
Sequence в Swift — это базовая единица итерации, которая требует от типа, чтобы он предоставлял новый итератор каждый раз при вызове makeIterator().Collection расширяет Sequence, обеспечивая многократную итерацию, стабильный порядок и доступ к индексам, что позволяет оптимизировать производительность.for … in фактически преобразуется в вызов makeIterator() и последующий вызов next() для получения элементов, что позволяет избежать ошибок при изменении коллекции во время итерации.Swift Concurrency вводит AsyncSequence и AsyncIteratorProtocol, позволяя использовать асинхронные итераторы с поддержкой приостановки и обработки ошибок.struct Countdown: Sequence {
let start: Int
func makeIterator() -> Iterator {
Iterator(current: start)
}
struct Iterator: IteratorProtocol {
var current: Int
mutating func next() -> Int? {
guard current >= 0 else { return nil }
defer { current -= 1 }
return current
}
}
}Please open Telegram to view this post
VIEW IN TELEGRAM
👍5
Using MainActor.assumeIsolated to Solve Legacy API Compatibility Issues with Swift 6
😨 Многие устаревшие API Apple не адаптированы к строгой проверке параллелизма
💡 Метод MainActor.assumeIsolated позволяет безопасно создавать
❌ Несмотря на попытки добавить аннотации
А вы применяли эту функцию, кроме как при отладке?🤔
Swift 6, что создает сложности для разработчиков при компиляции кода.UIHostingController в синхронном контексте, что решает проблемы с компиляцией при использовании устаревших API в контексте примера из статьи.public static func assumeIsolated<T>(_ operation: @MainActor () throws -> T, file: StaticString = #fileID, line: UInt = #line) rethrows -> T where T : Sendable
@MainActor, компилятор Swift 6 продолжает выдавать ошибки, если код не соответствует требованиям изоляции.А вы применяли эту функцию, кроме как при отладке?
Please open Telegram to view this post
VIEW IN TELEGRAM
👍5
Safer Swift: How ~Copyable Prevents Hidden Bugs
❓ Протокол
⚠️ Копирование структуры, содержащей указатель на файл, может привести к ошибкам, когда оба экземпляра записывают в один и тот же файл.
✔️ Добавление
🖥 Краткая справка по модификаторам:
~Copyable в Swift 5.9 предотвращает неявное копирование объектов, требуя явного управления владением данными.~Copyable к структуре предотвращает компиляцию кода, если происходит попытка использовать объект после его передачи.borrow (временный доступ для чтения), consume (полное владение) и inout (временный доступ для изменения).struct FileHandleWrapper: ~Copyable {
let handle: UnsafeMutablePointer<FILE>
init(path: String, mode: String) {
guard let file = fopen(path, mode) else {
fatalError("Failed to open file")
}
self.handle = file
}
func write(_ text: String) {
fputs(text, handle)
}
deinit {
print("Closing file handle")
fclose(handle)
}
}Please open Telegram to view this post
VIEW IN TELEGRAM
🔥2