Mercurial > hg > nsaunier > traffic-intelligence
comparison python/traffic_engineering.py @ 206:82b4101d9a2f
re-arranged and commnted signal cycle calculations
| author | Nicolas Saunier <nicolas.saunier@polymtl.ca> |
|---|---|
| date | Tue, 03 Apr 2012 01:11:29 -0400 |
| parents | aeaaf5579b46 |
| children | f65b828e5521 |
comparison
equal
deleted
inserted
replaced
| 205:aeaaf5579b46 | 206:82b4101d9a2f |
|---|---|
| 142 if sum(proportions) == 1: | 142 if sum(proportions) == 1: |
| 143 self.volume = volume | 143 self.volume = volume |
| 144 self.types = types | 144 self.types = types |
| 145 self.proportions = proportions | 145 self.proportions = proportions |
| 146 self.equivalents = equivalents | 146 self.equivalents = equivalents |
| 147 self.nLanes = nLanes | 147 self.nLanes = nLanes # unused |
| 148 else: | 148 else: |
| 149 pass | 149 pass |
| 150 | 150 |
| 151 def getPCUVolume(self): | 151 def getPCUVolume(self): |
| 152 '''Returns the passenger-car equivalent for the input volume''' | 152 '''Returns the passenger-car equivalent for the input volume''' |
| 164 self.mvtEquivalent = mvtEquivalent | 164 self.mvtEquivalent = mvtEquivalent |
| 165 | 165 |
| 166 def getTVUVolume(self): | 166 def getTVUVolume(self): |
| 167 return self.mvtEquivalent*self.volume.getPCUVolume() | 167 return self.mvtEquivalent*self.volume.getPCUVolume() |
| 168 | 168 |
| 169 class IntersectionApproach: | 169 class IntersectionApproach: # should probably not be used |
| 170 def __init__(self, leftTurnVolume, throughVolume, rightTurnVolume): | 170 def __init__(self, leftTurnVolume, throughVolume, rightTurnVolume): |
| 171 self.leftTurnVolume = leftTurnVolume | 171 self.leftTurnVolume = leftTurnVolume |
| 172 self.throughVolume = throughVolume | 172 self.throughVolume = throughVolume |
| 173 self.rightTurnVolume = rightTurnVolume | 173 self.rightTurnVolume = rightTurnVolume |
| 174 | 174 |
| 183 self.nLanes = nLanes | 183 self.nLanes = nLanes |
| 184 | 184 |
| 185 def getTVUVolume(self): | 185 def getTVUVolume(self): |
| 186 return sum([mvt.getTVUVolume() for mvt in self.movements]) | 186 return sum([mvt.getTVUVolume() for mvt in self.movements]) |
| 187 | 187 |
| 188 def getCharge(self, saturationVolume): | |
| 189 return self.getTVUVolume()/(self.nLanes*saturationVolume) | |
| 190 | |
| 188 def checkProtectedLeftTurn(leftMvt, opposedThroughMvt): | 191 def checkProtectedLeftTurn(leftMvt, opposedThroughMvt): |
| 189 '''Checks if one of the main two conditions on left turn is verified | 192 '''Checks if one of the main two conditions on left turn is verified |
| 190 The lane groups should contain left and through movement''' | 193 The lane groups should contain left and through movement''' |
| 191 return leftMvt.volume >= 200 or leftMvt.volume*opposedThroughMvt.volume/opposedThroughMvt.nLanes > 50000 | 194 return leftMvt.volume >= 200 or leftMvt.volume*opposedThroughMvt.volume/opposedThroughMvt.nLanes > 50000 |
| 192 | 195 |
| 193 def optimalCycle(lostTime, criticalCharge, rounding=True): | 196 def optimalCycle(lostTime, criticalCharge): |
| 194 if rounding: | 197 return (1.5*lostTime+5)/(1-criticalCharge) |
| 195 return ceil((1.5*lostTime+5)/(1-criticalCharge)) | 198 |
| 196 else: | 199 def minimumCycle(lostTime, criticalCharge, degreeSaturation=1.): |
| 197 return (1.5*lostTime+5)/(1-criticalCharge) | 200 'degree of saturation can be used as the peak hour factor too' |
| 201 return lostTime/(1-criticalCharge/degreeSaturation) | |
| 198 | 202 |
| 199 class Cycle: | 203 class Cycle: |
| 200 '''Class to compute optimal cycle and the split of effective green times''' | 204 '''Class to compute optimal cycle and the split of effective green times''' |
| 201 def __init__(self, phases, lostTime, saturationVolume): | 205 def __init__(self, phases, lostTime, saturationVolume): |
| 202 '''phases is a list of phases | 206 '''phases is a list of phases |
| 203 a phase is a list of lanegroups''' | 207 a phase is a list of lanegroups''' |
| 204 self.phases = phases | 208 self.phases = phases |
| 205 self.lostTime = lostTime | 209 self.lostTime = lostTime |
| 206 self.saturationVolume = saturationVolume | 210 self.saturationVolume = saturationVolume |
| 207 | 211 |
| 208 def computeCycle(self): | 212 def computeCriticalCharges(self): |
| 209 self.criticalCharges = [] | 213 self.criticalCharges = [] |
| 210 for phase in self.phases: | 214 for phase in self.phases: |
| 211 self.criticalCharges.append(max([lg.getTVUVolume() for lg in phase])/(lg.nLanes*self.saturationVolume)) | 215 self.criticalCharges.append(max([lg.getCharge(self.saturationVolume) for lg in phase])) |
| 212 | |
| 213 self.criticalCharge = sum(self.criticalCharges) | 216 self.criticalCharge = sum(self.criticalCharges) |
| 214 self.C0 = optimalCycle(self.lostTime, self.criticalCharge) | 217 |
| 215 return self.C0 | 218 def computeOptimalCycle(self): |
| 219 self.computeCriticalCharges() | |
| 220 self.C = optimalCycle(self.lostTime, self.criticalCharge) | |
| 221 return self.C | |
| 222 | |
| 223 def computeMinimumCycle(self, degreeSaturation=1.): | |
| 224 self.computeCriticalCharges() | |
| 225 self.C = minimumCycle(self.lostTime, self.criticalCharge, degreeSaturation) | |
| 226 return self.C | |
| 216 | 227 |
| 217 def computeEffectiveGreen(self): | 228 def computeEffectiveGreen(self): |
| 218 from numpy import round | 229 from numpy import round |
| 219 self.computeCycle() # in case it was not done before | 230 #self.computeCycle() # in case it was not done before |
| 220 effectiveGreenTime = self.C0-self.lostTime | 231 effectiveGreenTime = self.C-self.lostTime |
| 221 self.effectiveGreens = [round(c*effectiveGreenTime/self.criticalCharge,1) for c in self.criticalCharges] | 232 self.effectiveGreens = [round(c*effectiveGreenTime/self.criticalCharge,1) for c in self.criticalCharges] |
| 222 return self.effectiveGreens | 233 return self.effectiveGreens |
| 223 | 234 |
| 224 | 235 |
| 225 def computeInterGreen(perceptionReactionTime, initialSpeed, intersectionLength, vehicleAverageLength = 6, deceleration = 3): | 236 def computeInterGreen(perceptionReactionTime, initialSpeed, intersectionLength, vehicleAverageLength = 6, deceleration = 3): |
