Instantly share code, notes, and snippets.

@nvbn /commute.py
Last active May 17, 2018

Embed
What would you like to do?
import json
from datetime import datetime
from collections import namedtuple
from itertools import groupby, takewhile
from statistics import median, mean
from matplotlib import pyplot
import numpy as np
from geopy.distance import geodesic
Point = namedtuple('Point', 'latitude, longitude, datetime')
def read_points():
with open('data.json') as f:
data = json.load(f)
for point in data['locations']:
yield Point(
point['latitudeE7'] / 10 ** 7,
point['longitudeE7'] / 10 ** 7,
datetime.fromtimestamp(int(point['timestampMs']) / 1000)
)
home = (52.350879, 4.893817)
work = (52.3657573, 4.8980648)
max_distance = 0.050
from_date = datetime(2017, 11, 1)
from_hour = 7
to_hour = 12
points = read_points()
after_move = takewhile(lambda point: point.datetime >= from_date, points)
work_days = (point for point in after_move
if point.datetime.weekday() < 5)
commute_time = (point for point in work_days
if from_hour <= point.datetime.hour < to_hour)
by_days = groupby(commute_time, key=lambda point: point.datetime.date())
def last_at_home(points):
result = None
for point in points:
if geodesic(home, point[:2]).km <= max_distance:
result = point
return result
def first_at_work(points, after):
for point in points:
if point.datetime > after.datetime and geodesic(work, point[:2]).km <= max_distance:
return point
Commute = namedtuple('Commute', 'day, start, end, took')
def get_commute():
for day, points in by_days:
points = [*points][::-1]
start = last_at_home(points)
if start is None:
continue
end = first_at_work(points, start)
if end is None:
continue
yield Commute(
day, start.datetime, end.datetime, end.datetime - start.datetime,
)
commutes = [*get_commute()][::-1]
fig, ax = pyplot.subplots()
ax.plot([commute.day for commute in commutes],
[commute.took.total_seconds() / 60 for commute in commutes])
ax.set(xlabel='day', ylabel='commute (minutes)',
title='Daily commute')
ax.grid()
pyplot.show()
# http://www.knmi.nl/nederland-nu/klimatologie/daggegevens
from dateutil.parser import parse
Weather = namedtuple('Weather', 'windspeed, temperature, wind_direction')
def read_weather():
result = {}
with open('weather.txt') as f:
for line in f.readlines():
if not line.startswith(' '):
continue
data = [part.strip() for part in line.split(',')]
result[parse(data[1]).date()] = Weather(
int(data[4]) / 10,
int(data[11]) / 10,
int(data[2]),
)
return result
weather = read_weather()
normalized = [commute for commute in commutes
if commute.took.total_seconds() < 60 * 20]
fig, ax = pyplot.subplots()
ax.grid()
ax.scatter([commute.took.total_seconds() / 60 for commute in normalized],
[weather[commute.day].windspeed for commute in normalized])
ax.set(xlabel='Commute time', ylabel='Wind speed',
title='Commute and wind')
ax.legend()
pyplot.show()
from mpl_toolkits.mplot3d import Axes3D
fig, ax = pyplot.subplots(subplot_kw={'projection': '3d'})
ax.grid()
ax.scatter([weather[commute.day].temperature for commute in normalized],
[weather[commute.day].windspeed for commute in normalized],
[commute.took.total_seconds() / 60 for commute in normalized])
ax.set(xlabel='Wind speed', ylabel='Temperature', zlabel='Commute time',
title='Commute and weather')
ax.legend()
pyplot.show()
from matplotlib import cm
colors = iter(cm.Reds(np.linspace(0, 1, len(normalized))))
fig, ax = pyplot.subplots()
ax.grid()
for commute in sorted(normalized, key=lambda commute: commute.took.total_seconds() / 60):
ax.scatter(weather[commute.day].windspeed,
weather[commute.day].wind_direction,
color=next(colors))
ax.set(xlabel='Wind speed', ylabel='Wind direction',
title='Commute and wind')
ax.grid()
pyplot.show()
from matplotlib import cm
colors = iter(cm.Reds(np.linspace(0, 1, len(normalized))))
fig, ax = pyplot.subplots(subplot_kw={'projection': 'polar'})
for commute in sorted(normalized, key=lambda commute: commute.took.total_seconds() / 60):
ax.scatter(weather[commute.day].wind_direction,
weather[commute.day].windspeed,
color=next(colors))
ax.set(title='Commute and wind')
ax.grid()
pyplot.show()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment