den saknade manualen
för snabb utveckling
guiden Jag önskar att jag hade när jag började
gå med i 20 000 + utvecklare som lär dig om Swift Development
ladda ner din gratis kopia
om du tittar på det här antar jag att du är bekant med Swift extensions. Med ett Swift-tillägg kan du lägga till funktionalitet i en typ, en klass, en struktur, en enum eller ett protokoll. Men förlängningar är kraftfullare än så. I det här avsnittet vill jag visa dig fyra smarta användningar av Swift extensions.
Protokollkonformans
Swift-programmeringsspråket nämner att tillägg kan användas för att anpassa en befintlig typ till ett protokoll. Även om detta inte är nytt eller revolutionerande kan det också hjälpa dig att hålla din kod organiserad.
ta protokollen UITableViewDataSource
och UITableViewDelegate
som ett exempel. Det här exemplet kan se bekant ut. Det här är bra, men det resulterar i en lång klassimplementering som kan bli svår att navigera över tiden.
import UIKitclass ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource { ...}
du kan hålla din kod organiserad genom att skapa ett tillägg för varje protokoll som typen överensstämmer med.
import UIKitclass ViewController: UIViewController { ...}extension ViewController: UITableViewDataSource { ...}extension ViewController: UITableViewDelegate { ...}
navigering av källfiler blir också lättare om du gör det till en vana att använda hoppfältet högst upp i xcodes källredigerare.
bevara Initializers
jag lärde mig nästa trick från Chris Eidhof. För det här exemplet måste vi först definiera en struktur, Person
. Strukturen definierar två konstanta egenskaper av typen String
, first
och last
.
struct Person { // MARK: - Properties let first: String let last: String}
Swift skapar generöst en initialiserare för oss, init(first:last:)
, som vi kan använda för att instantiera en instans av Person
– strukturen. Det här är inte nytt.
let john = Person(first: "John", last: "Doe")
tyvärr är initialiseraren inte längre tillgänglig om vi definierar en anpassad initialiserare i strukturens definition.
struct Person { // MARK: - Properties let first: String let last: String // MARK: - Initialization init(dictionary: ) { self.first = dictionary ?? "John" self.last = dictionary ?? "Doe" }}
lyckligtvis har vi en enkel lösning för att lösa problemet. Vi skapar ett tillägg för Person
– strukturen där vi definierar den anpassade initialiseraren.
struct Person { // MARK: - Properties let first: String let last: String}extension Person { // MARK: - Initialization init(dictionary: ) { self.first = dictionary ?? "John" self.last = dictionary ?? "Doe" }}
Kodseparation
vi kan ta det föregående exemplet ett steg längre. För några år sedan skisserade Natasha Murashev en teknik som använder tillägg för att skilja tillstånd från beteende. Om vi tillämpar denna teknik på föregående exempel slutar vi med något liknande.
struct Person { // MARK: - Properties let first: String let last: String}extension Person { // MARK: - Initialization init(dictionary: ) { self.first = dictionary ?? "John" self.last = dictionary ?? "Doe" } // MARK: - Public API var asDictionary: { return }}
typdefinitionen definierar bara de lagrade egenskaperna. En förlängning skapas för typens beteende, det vill säga metoder och beräknade egenskaper. Resultatet är en tydlig separation av tillstånd (lagrade egenskaper) och beteende (metoder och beräknade egenskaper).
vi kan ta detta ett steg längre genom att skapa en andra privat förlängning för privat beteende.
struct Person { // MARK: - Properties let first: String let last: String}extension Person { ...}private extension Person { ...}
Kodseparation och organisation är mycket lätt att göra med tillägg. Jag använder det hela tiden. Om du saknar Objective-C: s header-filer är det här ett bra alternativ.
kapslade typer
Swift-programmeringsspråket nämner att tillägg också låter dig definiera och använda kapslade typer. Men jag tycker att den här funktionen är undervärderad. Jag använder det i varje Swift-projekt, till exempel för att definiera konstanter.
för några månader sedan publicerade jag en handledning om att bygga en anpassad kontroll med en bitmask. I den handledningen lagrar vi raw-värdet för bitmasken i användarstandarddatabasen.
// MARK: - [email protected] func scheduleDidChange(_ sender: SchedulePicker) { // Helpers let userDefaults = UserDefaults.standard // Store Value let scheduleRawValue = sender.schedule.rawValue userDefaults.set(scheduleRawValue, forKey: UserDefaults.Keys.schedule)}
istället för att använda en sträng bokstavlig använder vi en konstant. Vi skapar ett tillägg för klassen UserDefaults
där vi definierar ett enum utan Fall, Keys
. Enum definierar en statisk konstant egenskap av typen String
, schedule
.
extension UserDefaults { enum Keys { static let schedule = "schedule" }}
resultatet är ganska trevligt om du frågar mig. Inte bara kan vi gruppera konstanter och undvika bokstäver som är utspridda i kodbasen, vi namnrymder också konstanterna. Med andra ord är konstanterna lätta att komma ihåg och ge mening.
UserDefaults.Keys.schedule
med lanseringen av Swift 3 antog Apple en liknande teknik i några av sina ramar.
Notification.Name.UIApplicationWillTerminate
Vad är nästa
tillägg är ganska kraftfulla i Swift och teknikerna jag visade i denna handledning är bara några exempel på vad som är möjligt.
den saknade manualen
för snabb utveckling
guiden Jag önskar att jag hade när jag började
gå 20,000 + Utvecklare lära sig om Swift utveckling
ladda ner din gratis kopia