Mercurial > hg > nsaunier > traffic-intelligence
comparison python/traffic_engineering.py @ 34:388a5a25fe92
Code for lab5 works
| author | Nicolas Saunier <nico@confins.net> |
|---|---|
| date | Sun, 11 Apr 2010 02:23:48 -0400 |
| parents | 4bd7cc69b6cd |
| children | 571b11304ec9 |
comparison
equal
deleted
inserted
replaced
| 33:4bd7cc69b6cd | 34:388a5a25fe92 |
|---|---|
| 29 v = 0 | 29 v = 0 |
| 30 for p, e in zip(self.proportions, self.equivalents): | 30 for p, e in zip(self.proportions, self.equivalents): |
| 31 v += p*e | 31 v += p*e |
| 32 return v*self.volume | 32 return v*self.volume |
| 33 | 33 |
| 34 class IntersectionMouvement: | 34 class IntersectionMovement: |
| 35 '''Represents an intersection movement | 35 '''Represents an intersection movement |
| 36 with a volume, a type (through, left or right) | 36 with a volume, a type (through, left or right) |
| 37 and an equivalent for movement type''' | 37 and an equivalent for movement type''' |
| 38 def __init__(self, volume, type, mvtEquivalent = 1): | 38 def __init__(self, volume, type, mvtEquivalent = 1): |
| 39 self.volume = volume | 39 self.volume = volume |
| 40 self.type = type | 40 self.type = type |
| 41 self.mvtEquivalent = mvtEquivalent | 41 self.mvtEquivalent = mvtEquivalent |
| 42 | 42 |
| 43 def getTVUVolume(self): | 43 def getTVUVolume(self): |
| 53 return self.leftTurnVolume.getPCEVolume()*leftTurnEquivalent+self.throughVolume.getPCEVolume()*throughEquivalent+self.rightTurnVolume.getPCEVolume()*rightTurnEquivalent | 53 return self.leftTurnVolume.getPCEVolume()*leftTurnEquivalent+self.throughVolume.getPCEVolume()*throughEquivalent+self.rightTurnVolume.getPCEVolume()*rightTurnEquivalent |
| 54 | 54 |
| 55 class LaneGroup: | 55 class LaneGroup: |
| 56 '''Class that represents a group of mouvements''' | 56 '''Class that represents a group of mouvements''' |
| 57 | 57 |
| 58 def __init__(self): | 58 def __init__(self, movements, nLanes): |
| 59 self.mouvements = {'left': [], | 59 self.movements = movements |
| 60 'through': [], | 60 self.nLanes = nLanes |
| 61 'right': []} | |
| 62 | 61 |
| 63 # all the add*Mvt should add a IntersectionMovement instance | 62 def getTVUVolume(self): |
| 64 def addLeftMvt(self, vol): | 63 return sum([mvt.getTVUVolume() for mvt in self.movements]) |
| 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 | 64 |
| 78 def checkProtectedLeftTurn(leftMvt, opposedThroughMvt): | 65 def checkProtectedLeftTurn(leftMvt, opposedThroughMvt): |
| 79 '''Checks if one of the main two conditions on left turn is verified | 66 '''Checks if one of the main two conditions on left turn is verified |
| 80 The lane groups should contain left and through movement''' | 67 The lane groups should contain left and through movement''' |
| 81 return leftMvt.volume >= 200 or leftMvt.volume*opposedMvt.volume/opposedMvt.nLanes > 50000 | 68 return leftMvt.volume >= 200 or leftMvt.volume*opposedThroughMvt.volume/opposedThroughMvt.nLanes > 50000 |
| 82 | 69 |
| 83 def optimalCycle(lostTime, criticalCharge): | 70 def optimalCycle(lostTime, criticalCharge, rounding=True): |
| 84 return ceil((1.5*lostTime+5)/(1-criticalCharge)) | 71 if rounding: |
| 72 return ceil((1.5*lostTime+5)/(1-criticalCharge)) | |
| 73 else: | |
| 74 return (1.5*lostTime+5)/(1-criticalCharge) | |
| 75 | |
| 76 class Cycle: | |
| 77 '''Class to compute optimal cycle and the split of effective green times''' | |
| 78 def __init__(self, phases, lostTime, saturationVolume): | |
| 79 '''phases is a list of phases | |
| 80 a phase is a list of lanegroups''' | |
| 81 self.phases = phases | |
| 82 self.lostTime = lostTime | |
| 83 self.saturationVolume = saturationVolume | |
| 84 | |
| 85 def computeCycle(self): | |
| 86 self.criticalCharges = [] | |
| 87 for phase in self.phases: | |
| 88 self.criticalCharges.append(max([lg.getTVUVolume() for lg in phase])/(lg.nLanes*self.saturationVolume)) | |
| 89 | |
| 90 self.criticalCharge = sum(self.criticalCharges) | |
| 91 self.C0 = optimalCycle(self.lostTime, self.criticalCharge) | |
| 92 return self.C0 | |
| 93 | |
| 94 def computeEffectiveGreen(self): | |
| 95 from numpy import round | |
| 96 self.computeCycle() # in case it was not done before | |
| 97 effectiveGreenTime = self.C0-self.lostTime | |
| 98 self.effectiveGreens = [round(c*effectiveGreenTime/self.criticalCharge,1) for c in self.criticalCharges] | |
| 99 return self.effectiveGreens | |
| 100 | |
| 85 | 101 |
| 86 def computeInterGreen(perceptionReactionTime, initialSpeed, intersectionLength, vehicleAverageLength = 6, deceleration = 3): | 102 def computeInterGreen(perceptionReactionTime, initialSpeed, intersectionLength, vehicleAverageLength = 6, deceleration = 3): |
| 87 '''Computes the intergreen time (yellow/amber plus all red time) | 103 '''Computes the intergreen time (yellow/amber plus all red time) |
| 88 Deceleration is positive | 104 Deceleration is positive |
| 89 All variables should be in the same units''' | 105 All variables should be in the same units''' |
