Mercurial > hg > nsaunier > traffic-intelligence
comparison python/traffic_engineering.py @ 33:4bd7cc69b6cd
added traffic engineering utilities with first version of LaneGroups
| author | Nicolas Saunier <nico@confins.net> |
|---|---|
| date | Sat, 10 Apr 2010 20:46:33 -0400 |
| parents | |
| children | 388a5a25fe92 |
comparison
equal
deleted
inserted
replaced
| 32:48e56179c39e | 33:4bd7cc69b6cd |
|---|---|
| 1 #! /usr/bin/env python | |
| 2 ''' Traffic Engineering Tools.''' | |
| 3 | |
| 4 from math import ceil | |
| 5 | |
| 6 __metaclass__ = type | |
| 7 | |
| 8 ######################### | |
| 9 # traffic signals | |
| 10 ######################### | |
| 11 | |
| 12 class Volume: | |
| 13 '''Class to represent volumes with varied vehicule types ''' | |
| 14 def __init__(self, volume, types = ['pc'], proportions = [1], equivalents = [1], nLanes = 1): | |
| 15 '''mvtEquivalent is the equivalent if the movement is right of left turn''' | |
| 16 | |
| 17 # check the sizes of the lists | |
| 18 if sum(proportions) == 1: | |
| 19 self.volume = volume | |
| 20 self.types = types | |
| 21 self.proportions = proportions | |
| 22 self.equivalents = equivalents | |
| 23 self.nLanes = nLanes | |
| 24 else: | |
| 25 pass | |
| 26 | |
| 27 def getPCEVolume(self): | |
| 28 '''Returns the passenger-car equivalent for the input volume''' | |
| 29 v = 0 | |
| 30 for p, e in zip(self.proportions, self.equivalents): | |
| 31 v += p*e | |
| 32 return v*self.volume | |
| 33 | |
| 34 class IntersectionMouvement: | |
| 35 '''Represents an intersection movement | |
| 36 with a volume, a type (through, left or right) | |
| 37 and an equivalent for movement type''' | |
| 38 def __init__(self, volume, type, mvtEquivalent = 1): | |
| 39 self.volume = volume | |
| 40 self.type = type | |
| 41 self.mvtEquivalent = mvtEquivalent | |
| 42 | |
| 43 def getTVUVolume(self): | |
| 44 return self.mvtEquivalent*self.volume.getPCEVolume() | |
| 45 | |
| 46 class IntersectionApproach: | |
| 47 def __init__(self, leftTurnVolume, throughVolume, rightTurnVolume): | |
| 48 self.leftTurnVolume = leftTurnVolume | |
| 49 self.throughVolume = throughVolume | |
| 50 self.rightTurnVolume = rightTurnVolume | |
| 51 | |
| 52 def getTVUVolume(self, leftTurnEquivalent = 1, throughEquivalent = 1, rightTurnEquivalent = 1): | |
| 53 return self.leftTurnVolume.getPCEVolume()*leftTurnEquivalent+self.throughVolume.getPCEVolume()*throughEquivalent+self.rightTurnVolume.getPCEVolume()*rightTurnEquivalent | |
| 54 | |
| 55 class LaneGroup: | |
| 56 '''Class that represents a group of mouvements''' | |
| 57 | |
| 58 def __init__(self): | |
| 59 self.mouvements = {'left': [], | |
| 60 'through': [], | |
| 61 'right': []} | |
| 62 | |
| 63 # all the add*Mvt should add a IntersectionMovement instance | |
| 64 def addLeftMvt(self, vol): | |
| 65 self.mouvements['left'].append(vol) | |
| 66 | |
| 67 def addRightMvt(self, vol): | |
| 68 self.mouvements['right'].append(vol) | |
| 69 | |
| 70 def addThroughMvt(self, vol): | |
| 71 self.mouvements['through'].append(vol) | |
| 72 | |
| 73 def getTVUVolume(self, leftTurnEquivalent = 1, throughEquivalent = 1, rightTurnEquivalent = 1): | |
| 74 return leftTurnEquivalent*sum([m.getPCEVolume() for m in mouvements['left']])\ | |
| 75 +rightTurnEquivalent*sum([m.getPCEVolume() for m in mouvements['right']])\ | |
| 76 +throughTurnEquivalent*sum([m.getPCEVolume() for m in mouvements['through']]) | |
| 77 | |
| 78 def checkProtectedLeftTurn(leftMvt, opposedThroughMvt): | |
| 79 '''Checks if one of the main two conditions on left turn is verified | |
| 80 The lane groups should contain left and through movement''' | |
| 81 return leftMvt.volume >= 200 or leftMvt.volume*opposedMvt.volume/opposedMvt.nLanes > 50000 | |
| 82 | |
| 83 def optimalCycle(lostTime, criticalCharge): | |
| 84 return ceil((1.5*lostTime+5)/(1-criticalCharge)) | |
| 85 | |
| 86 def computeInterGreen(perceptionReactionTime, initialSpeed, intersectionLength, vehicleAverageLength = 6, deceleration = 3): | |
| 87 '''Computes the intergreen time (yellow/amber plus all red time) | |
| 88 Deceleration is positive | |
| 89 All variables should be in the same units''' | |
| 90 if deceleration > 0: | |
| 91 return [perceptionReactionTime+initialSpeed/(2*deceleration), (intersectionLength+vehicleAverageLength)/initialSpeed] | |
| 92 else: | |
| 93 print 'Issue deceleration should be strictly positive' | |
| 94 return None |
