Last active
May 26, 2017 09:35
-
-
Save juhagman/46041956a595b40fe703a81c32703d15 to your computer and use it in GitHub Desktop.
Swift playgrounds code to filter Wikimedia browser stats
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
let tab = CharacterSet(charactersIn: "\t") | |
let newline = CharacterSet(charactersIn: "\n") | |
let fmt = DateFormatter() ; fmt.dateFormat = "YYYY-mm-DD" | |
let dateRanges = [ | |
(fmt.date(from: "2015-01-01"), fmt.date(from: "2016-01-01")), | |
(fmt.date(from: "2016-01-01"), fmt.date(from: "2017-01-01")), | |
(fmt.date(from: "2017-01-01"), fmt.date(from: "2018-01-01")), | |
] | |
struct DataPoint { | |
let os, osVersion, browser, browserVersion: String | |
let value: Double | |
let date: Date | |
init(os: String, osVersion: String, browser: String, browserVersion: String, value: Double, date: Date) | |
{ | |
self.os = os | |
self.osVersion = osVersion | |
self.browser = browser | |
self.browserVersion = browserVersion | |
self.value = value | |
self.date = date | |
} | |
init?(string s: String) { | |
let comps = s.components(separatedBy: tab) | |
guard comps.count == 6, | |
let v = comps.last as NSString?, | |
let d = fmt.date(from: comps[0]) | |
else { return nil } | |
self.init(os: comps[1], osVersion: comps[2], | |
browser: comps[3], browserVersion: comps[4], | |
value: v.doubleValue, date: d) | |
} | |
} | |
func readStats() -> String { | |
let url = URL(string: "https://analytics.wikimedia.org/datasets/periodic/reports/metrics/browser/all_sites_by_os_and_browser_percent.tsv") | |
return try! String(contentsOf: url!) | |
} | |
func ratio(browser: String, data: [DataPoint]) -> Double { | |
let browserSum = data.filter { $0.browser == browser } | |
.reduce(0) { $0 + $1.value } | |
let allSum = data.reduce(0) { $0 + $1.value } | |
return browserSum / allSum | |
} | |
let osxData = readStats() | |
.components(separatedBy: newline) | |
.flatMap { DataPoint.init(string: $0) } | |
.filter { $0.os == "Mac OS X" } | |
for (start, end) in dateRanges { | |
guard let start = start, let end = end else { continue } | |
let rangedData = osxData.filter { start <= $0.date && $0.date < end } | |
let safariPercentage = ratio(browser: "Safari", data: rangedData) * 100.0 | |
let chromePercentage = ratio(browser: "Chrome", data: rangedData) * 100.0 | |
let dateRange = "\(fmt.string(from: start)) - \(fmt.string(from: end))" | |
let output = String(format: "%@ Safari: %2.1f%% Chrome: %2.1f%%", dateRange, safariPercentage, chromePercentage) | |
print(output) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Refactored this to have a bit nicer structure and it now reports the Safari and Chrome results by time ranges.
Running this on Swift Playground or Xcode Playground results in