From c101d9dd04195427ade3dee8270c06e8bfe18ca2 Mon Sep 17 00:00:00 2001 From: Brent Simmons Date: Sun, 22 Oct 2017 11:08:51 -0700 Subject: [PATCH] Maintain url-to-feed and feedID-to-feed dictionaries to make lookups faster. This makes OPML importing very fast. --- Frameworks/Account/Account.swift | 42 ++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/Frameworks/Account/Account.swift b/Frameworks/Account/Account.swift index cedea2658..ba562f5e1 100644 --- a/Frameworks/Account/Account.swift +++ b/Frameworks/Account/Account.swift @@ -49,6 +49,8 @@ public final class Account: DisplayNameProvider, UnreadCountProvider, Container, public var nameForDisplay = "" public let hashValue: Int public var children = [AnyObject]() + var urlToFeedDictionary = [String: Feed]() + var idToFeedDictionary = [String: Feed]() let settingsFile: String let dataFolder: String let database: Database @@ -217,10 +219,14 @@ public final class Account: DisplayNameProvider, UnreadCountProvider, Container, if let folder = folder { didAddFeed = folder.addFeed(uniquedFeed) + if didAddFeed { + addToFeedDictionaries(uniquedFeed) + } } else { if !topLevelObjectsContainsFeed(uniquedFeed) { children += [uniquedFeed] + addToFeedDictionaries(uniquedFeed) dirty = true postChildrenDidChangeNotification() } @@ -380,6 +386,7 @@ private extension Account { return } children = objects(with: childrenArray) + rebuildFeedDictionaries() if let savedUnreadCount = d[Key.unreadCount] as? Int { DispatchQueue.main.async { @@ -461,6 +468,26 @@ private extension Account { private extension Account { + func rebuildFeedDictionaries() { + + var urlDictionary = [String: Feed]() + var idDictionary = [String: Feed]() + + flattenedFeeds().forEach { (feed) in + urlDictionary[feed.url] = feed + idDictionary[feed.feedID] = feed + } + + urlToFeedDictionary = urlDictionary + idToFeedDictionary = idDictionary + } + + func addToFeedDictionaries(_ feed: Feed) { + + urlToFeedDictionary[feed.url] = feed + idToFeedDictionary[feed.feedID] = feed + } + func topLevelObjectsContainsFeed(_ feed: Feed) -> Bool { return children.contains(where: { (object) -> Bool in @@ -526,6 +553,21 @@ private extension Account { } } +// MARK: - Container Overrides + +extension Account { + + public func existingFeed(withURL url: String) -> Feed? { + + return urlToFeedDictionary[url] + } + + public func existingFeed(with feedID: String) -> Feed? { + + return idToFeedDictionary[feedID] + } +} + // MARK: - OPMLRepresentable extension Account: OPMLRepresentable {