"""Karma logging models.""" import math import random import pytz from django.conf import settings from django.db import models class PiLogManager(models.Manager): """Assemble some queries against PiLog.""" def simulate(self): """Add one more entry to the log, and return it.""" try: latest = self.latest() except PiLog.DoesNotExist: latest = PiLog.objects.create(simulation_x=0.0, simulation_y=0.0, total_count_inside=0, total_count=0) latest.save() inside = latest.total_count_inside total = latest.total_count x = random.random() y = random.random() total += 1 if math.hypot(x, y) < 1: inside += 1 newest = PiLog.objects.create(simulation_x=x, simulation_y=y, total_count_inside=inside, total_count=total) # TODO: remove the x, y return values, now that we track them in the object return newest, x, y class PiLog(models.Model): """Track pi as it is estimated over time.""" simulation_x = models.DecimalField(max_digits=11, decimal_places=10) simulation_y = models.DecimalField(max_digits=11, decimal_places=10) total_count_inside = models.PositiveIntegerField() total_count = models.PositiveIntegerField() created = models.DateTimeField(auto_now_add=True) objects = PiLogManager() class Meta: """Options for the PiLog class.""" get_latest_by = 'created' def __str__(self): """Provide string representation.""" tz = pytz.timezone(settings.TIME_ZONE) return "({0:d}/{1:d}) @ {2:s}".format(self.total_count_inside, self.total_count, self.created.astimezone(tz).strftime('%Y-%m-%d %H:%M:%S %Z')) @property def value(self): """Return this log entry's estimated value of pi.""" if self.total_count == 0: return 0.0 return 4.0 * int(self.total_count_inside) / int(self.total_count) @property def hit(self): """Return if this log entry is inside the unit circle.""" return math.hypot(self.simulation_x, self.simulation_y) < 1