public float ComputeUtility(IZone o, IZone d) { float sum = 0f; var flatO = ZoneSystem.GetFlatIndex(o.ZoneNumber); var flatD = ZoneSystem.GetFlatIndex(d.ZoneNumber); bool any = false; var zoneIndex = (flatO * Zones.Length + flatD) * Modes.Length; for (int mode = 0; mode < Modes.Length; mode++) { EnsureResult(flatO, mode); if (Modes[mode].Feasible(o, d, SimulationTime)) { var res = Modes[mode].CalculateV(o, d, SimulationTime); if (!float.IsNaN(res)) { float v = (float)Math.Exp(res); if (Adjustments != null) { v *= Adjustments.GiveAdjustment(o, d, mode, (int)CurrentInteractiveCategory); } CurrentUtility[zoneIndex + mode] = v; sum += v; any = true; } } } return(any ? sum : float.NaN); }
private void LoadProbabilityTable(string fileName, float[,] table) { using (CsvReader reader = new CsvReader(fileName)) { var numberOfColumns = reader.LoadLine(); int[] dIndex = new int[numberOfColumns - 1]; for (int i = 0; i < numberOfColumns - 1; i++) { reader.Get(out dIndex[i], i + 1); dIndex[i] = ZoneArray.GetFlatIndex(dIndex[i]); } // read in the headers while (!reader.EndOfFile) { numberOfColumns = reader.LoadLine(); if (numberOfColumns == 0) { // counter balance a blank line in the middle continue; } int o; reader.Get(out o, 0); o = ZoneArray.GetFlatIndex(o); for (int i = 0; i < numberOfColumns - 1; i++) { reader.Get(out table[o, dIndex[i]], i + 1); } } } }
public void Execute(ITashaHousehold household, int iteration) { var homeZone = _zones.GetFlatIndex(household.HomeZone.ZoneNumber); foreach (var person in household.Persons) { int emp = GetEmp(person); int occ = GetOcc(person); if (ValidPerson(emp, occ)) { var workerCategory = GetWorkerCategory(person, household); var empZone = person.EmploymentZone; if (empZone == null) { continue; } var flatEmpZone = _zones.GetFlatIndex(empZone.ZoneNumber); float expansionFactor = person.ExpansionFactor; _zonalEmployment[emp][occ][flatEmpZone] += expansionFactor; if (!ExternalPDs.Contains(empZone.PlanningDistrict)) { _zonalResidence[emp][occ][homeZone] += expansionFactor; } _zonalWorkerCategories[emp][occ][homeZone][flatEmpZone][workerCategory] += expansionFactor; } } }
/// <summary> /// The V for a trip whose mode is bike /// </summary> /// <param name="trip">The trip</param> /// <returns>The V for this trip</returns> public double CalculateV(ITrip trip) { float v = 0; ITashaPerson person = trip.TripChain.Person; GetPersonVariables(person, out float timeFactor, out float constant); v += constant; Time startTime = trip.ActivityStartTime; IZone origin = trip.OriginalZone; IZone destination = trip.DestinationZone; var o = _zoneSystem.GetFlatIndex(origin.ZoneNumber); var d = _zoneSystem.GetFlatIndex(destination.ZoneNumber); if (o == d) { v += IntrazonalConstant; } v += timeFactor * TravelTime(o, d, startTime).ToMinutes(); v += _zonalDestinationUtility[d]; if (person.Youth) { v += YouthFlag; } if (person.YoungAdult) { v += YoungAdultFlag; } return(v + GetPlanningDistrictConstant(startTime, origin.PlanningDistrict, destination.PlanningDistrict)); }
public bool GetAllData(IZone start, IZone end, Time time, out Time ivtt, out float cost) { float ivttTime, walkTime, waitTime, boardingtime; this.GetData(ZoneArray.GetFlatIndex(start.ZoneNumber), ZoneArray.GetFlatIndex(end.ZoneNumber), time, out ivttTime, out cost, out walkTime, out waitTime, out boardingtime); ivtt = Time.FromMinutes(ivttTime + walkTime + waitTime); if (this.NoWalkTimeInfeasible & (walkTime <= 0 & ivttTime <= 0)) { return(false); } return(true); }
private void CombineData(SparseArray <IZone> zones, float[][] matrix) { foreach (var source in DataSources) { foreach (var dataPoint in source.Read()) { var o = zones.GetFlatIndex(dataPoint.O); var d = zones.GetFlatIndex(dataPoint.D); matrix[o][d] += dataPoint.Data; } } }
private void ComputeLineHaull(float[][] currentTally, SparseArray <IZone> zoneArray, IZone[] zones, int m, float[][] data) { // this can't be in parallel since we are writing to the some access and egress data entries for (int i = 0; i < data.Length; i++) { if (data[i] == null) { continue; } for (int j = 0; j < data[i].Length; j++) { var totalTrips = data[i][j]; if (totalTrips <= 0f) { continue; } var choices = GetStationChoiceSplit(m, zones[i], zones[j]); if (choices == null) { continue; } var accessStations = choices.Item1; var egressStations = choices.Item2; if (egressStations == null) { continue; } var splits = choices.Item3; var totalSplits = 0f; for (int z = 0; z < accessStations.Length; z++) { if (accessStations[z] != null) { totalSplits += splits[z]; } } for (int z = 0; z < accessStations.Length; z++) { if (accessStations[z] == null | egressStations[z] == null) { break; } var accessZoneNumber = zoneArray.GetFlatIndex(accessStations[z].ZoneNumber); var egressZoneNumber = zoneArray.GetFlatIndex(egressStations[z].ZoneNumber); // no lock needed since we are doing it parallel in the i, so there will be no conflicts currentTally[accessZoneNumber][egressZoneNumber] += totalTrips * (splits[z] / totalSplits); } } } }
private void AddToMatrix(ITrip trip, float expFactor) { bool taken = false; var o = ZoneSystem.GetFlatIndex(trip.OriginalZone.ZoneNumber); var d = ZoneSystem.GetFlatIndex(trip.DestinationZone.ZoneNumber); var row = Data[o]; WriteLock.Enter(ref taken); Thread.MemoryBarrier(); row[d] += expFactor; if (taken) { WriteLock.Exit(true); } }
private void ComputeFromDestination(float[][] currentTally, SparseArray <IZone> zoneArray, IZone[] zones, int m, float[][] data) { Parallel.For(0, data.Length, new ParallelOptions() { MaxDegreeOfParallelism = Environment.ProcessorCount }, delegate(int j) { for (int i = 0; i < data.Length; i++) { if (data[i] == null || data[i][j] <= 0f) { continue; } var choices = GetStationChoiceSplit(m, zones[i], zones[j]); if (choices == null) { continue; } // check for egress stations first var stationZones = choices.Item2; if (stationZones == null) { // if there are no egress stations, use the access stations stationZones = choices.Item1; } var splits = choices.Item3; var totalTrips = data[i][j]; var totalSplits = 0f; for (int z = 0; z < stationZones.Length; z++) { if (stationZones[z] != null) { totalSplits += splits[z]; } } for (int z = 0; z < stationZones.Length; z++) { if (stationZones[z] == null) { break; } var flatZoneNumber = zoneArray.GetFlatIndex(stationZones[z].ZoneNumber); if (currentTally[flatZoneNumber] == null) { lock (data) { System.Threading.Thread.MemoryBarrier(); if (currentTally[flatZoneNumber] == null) { currentTally[flatZoneNumber] = new float[data[i].Length]; } } } // no lock needed since we are doing it parallel in the i, so there will be no conflicts currentTally[flatZoneNumber][j] += totalTrips * (splits[z] / totalSplits); } } }); }
private float[] LoadWorkerCategories(IZone[] zones, SparseArray <IZone> zoneArray) { if ((!ReloadWorkerCategories) & (WorkerCategories != null)) { return(WorkerCategories); } var ret = new float[zones.Length * NumberOfWorkerCategories]; using (CsvReader reader = new CsvReader(WorkerCategorySplits)) { //burn header reader.LoadLine(out int columns); // read data while (reader.LoadLine(out columns)) { if (columns < 3) { continue; } reader.Get(out int zone, 0); reader.Get(out int category, 1); reader.Get(out float probability, 2); zone = zoneArray.GetFlatIndex(zone); // categories are 1 indexed however we want 0 indexed category -= 1; if (zone < 0 | category < 0 | category >= NumberOfWorkerCategories) { continue; } ret[zone + (zones.Length * category)] = probability; } } return(WorkerCategories = ret); }
private int[] CreateStationIndexLookup(SparseArray <IZone> zoneSystem, IZone[] zones) { var lookup = zones.Select(z => zoneSystem.GetFlatIndex(z.ZoneNumber)).ToArray(); StationIndexLookup = lookup; return(lookup); }
private void LoadProbabilities(SparseArray <IZone> zoneSystem) { var zones = zoneSystem.GetFlatData(); ObservedDistribution = new float[zones.Length]; TotalTrips = new float[zones.Length]; using (CsvReader reader = new CsvReader(ObservedDistributionFile)) { // burn header reader.LoadLine(); // read in the rest of the data while (reader.LoadLine(out int columns)) { if (columns >= 2) { reader.Get(out int zone, 0); zone = zoneSystem.GetFlatIndex(zone); if (zone >= 0) { reader.Get(out float probability, 1); reader.Get(out float totalTrips, 2); ObservedDistribution[zone] = probability; TotalTrips[zone] = totalTrips; } } } } }
private float CalculateDATTime(Time time, IZone originalZone, int accessFlat, IZone destinationZone, bool access) { var origin = ZoneSystem.GetFlatIndex(originalZone.ZoneNumber); var destination = ZoneSystem.GetFlatIndex(destinationZone.ZoneNumber); if (access) { return((AutoNetwork.TravelTime(origin, accessFlat, time) + TransitNetwork.TravelTime(accessFlat, destination, time)).ToMinutes()); } else { return((TransitNetwork.TravelTime(origin, accessFlat, time) + AutoNetwork.TravelTime(accessFlat, destination, time)).ToMinutes()); } }
private float[][][] BuildData(string[] modeNames, SparseArray <IZone> zoneSystem, SparseArray <int> regions) { var modes = Root.AllModes.ToArray(); var data = new float[modes.Length][][]; var numberOfRegions = regions.GetFlatData().Length; for (int i = 0; i < data.Length; i++) { var row = data[i] = new float[numberOfRegions][]; for (int j = 0; j < row.Length; j++) { row[j] = new float[numberOfRegions]; } } using (CsvReader reader = new CsvReader(ZonalModeSplitFile)) { // burn header reader.LoadLine(); while (reader.LoadLine(out int columns)) { // ignore lines without the right number of columns if (columns == 4) { reader.Get(out string modeName, 0); reader.Get(out int originZone, 1); reader.Get(out int destinationZone, 2); reader.Get(out float expandedPersons, 3); data[ModeIndex(modeName, modeNames)][regions.GetFlatIndex(zoneSystem[originZone].RegionNumber)][regions.GetFlatIndex(zoneSystem[destinationZone].RegionNumber)] += expandedPersons; } } } return(data); }
/// <summary> /// The V for a trip whose mode is bike /// </summary> /// <param name="trip">The trip</param> /// <returns>The V for this trip</returns> public double CalculateV(ITrip trip) { float v = 0; var oZone = trip.OriginalZone; var dZone = trip.DestinationZone; var time = trip.ActivityStartTime; ITashaPerson person = trip.TripChain.Person; GetPersonVariables(person, out float timeFactor, out float constant); v += constant; v += UtilityAugmentation?.GetValueFromFlat(time, _zoneSystem.GetFlatIndex(oZone.ZoneNumber), _zoneSystem.GetFlatIndex(dZone.ZoneNumber)) ?? 0.0f; if (trip.OriginalZone == trip.DestinationZone) { v += IntrazonalConstant; } v += timeFactor * TravelTime(oZone, dZone, time).ToMinutes(); if (person.Youth) { v += YouthFlag; } if (person.YoungAdult) { v += YoungAdultFlag; } return(v); }
private float CalculateDATTime(SparseArray <IZone> _zoneSystem, INetworkData _autoNetwork, ITripComponentData _transitNetwork, Time time, IZone originalZone, int accessFlat, IZone destinationZone, bool access) { var origin = _zoneSystem.GetFlatIndex(originalZone.ZoneNumber); var destination = _zoneSystem.GetFlatIndex(destinationZone.ZoneNumber); if (access) { return((_autoNetwork.TravelTime(origin, accessFlat, time) + _transitNetwork.TravelTime(accessFlat, destination, time)).ToMinutes()); } else { return((_transitNetwork.TravelTime(origin, accessFlat, time) + _autoNetwork.TravelTime(accessFlat, destination, time)).ToMinutes()); } }
public double CalculateV(ITrip trip) { // compute the non human factors IZone originalZone = trip.OriginalZone; var o = ZoneArray.GetFlatIndex(originalZone.ZoneNumber); IZone destinationZone = trip.DestinationZone; var d = ZoneArray.GetFlatIndex(destinationZone.ZoneNumber); var p = trip.TripChain.Person; float perceivedTimeFactor, constant, costFactor; GetPersonVariables(p, out constant, out perceivedTimeFactor, out costFactor); float v = constant; // if Intrazonal float ivtt, walk, wait, perceivedTime, cost; if (Network.GetAllData(o, d, trip.TripStartTime, out ivtt, out walk, out wait, out perceivedTime, out cost)) { v += perceivedTime * perceivedTimeFactor + cost * costFactor; } else { return(float.NegativeInfinity); } //Apply trip purpose factors switch (trip.Purpose) { case Activity.Market: v += MarketFlag + ZonalDensityForActivitiesArray[d]; break; case Activity.IndividualOther: v += OtherFlag + ZonalDensityForActivitiesArray[d]; break; case Activity.Home: v += ZonalDensityForHomeArray[d]; break; default: v += ZonalDensityForActivitiesArray[d]; break; } v += GetPlanningDistrictConstant(trip.TripStartTime, originalZone.PlanningDistrict, destinationZone.PlanningDistrict); return((double)v); }
public double CalculateV(ITrip trip) { // compute the non human factors IZone originalZone = trip.OriginalZone; var o = ZoneArray.GetFlatIndex(originalZone.ZoneNumber); IZone destinationZone = trip.DestinationZone; var d = ZoneArray.GetFlatIndex(destinationZone.ZoneNumber); var p = trip.TripChain.Person; GetPersonVariables(p, out float constant, out float perceivedTimeFactor, out float costFactor); float v = constant; if (Network.GetAllData(o, d, trip.TripStartTime, out float ivtt, out float walk, out float wait, out float perceivedTime, out float cost)) { v += perceivedTime * perceivedTimeFactor + cost * costFactor; }
private void FillInPopulationByZone(SparseArray <IZone> zones, int numberOfZones, IDbCommand command, float[][][] populationByAge) { for (int j = 0; j < AgeSets.Count; j++) { populationByAge[j] = new float[EmploymentStatusString.Length][]; for (int i = 0; i < EmploymentStatusString.Length; i++) { populationByAge[j][i] = new float[numberOfZones]; command.CommandText = String.Format(@"SELECT [{3}].[{0}], SUM([{2}].[{1}]) FROM [{2}] INNER JOIN [{3}] ON [{2}].[{4}] = [{3}].[{4}] AND [{2}].[{5}] = [{3}].[{5}] WHERE [{2}].[{5}] = {6} AND [{3}].[{7}] = {8} AND [{2}].[{9}] >= {10} AND [{2}].[{9}] <= {11} AND [{2}].[{13}] = '{12}' GROUP BY [{3}].[{0}];", //0 ZoneNumberColumn, //1 ExpansionFactorColumnName, //2 PersonsTable, //3 HomeZoneTableName, //4 HouseholdIDColumn, //5 TTSYearColumn, //6 TTSYear, //7 ZoneSystemColumn, //8 ZoneSystemNumber, //9 AgeColumn, //10 AgeSets[j].Start, //11 AgeSets[j].Stop, //12 EmploymentStatusString[i], //13 EmploymentStatusColumn); using (var reader = command.ExecuteReader()) { while (reader.Read()) { var zone = reader.GetInt32(0); var index = zones.GetFlatIndex(zone); if (index >= 0) { populationByAge[j][i][index] = (float)reader.GetDouble(1); } } } } } }
private void LoadData(float[] data, IReadODData <float> readODData, int dataTypeOffset, SparseArray <IZone> zoneArray, int timesLoaded) { if (readODData == null) { return; } var zones = zoneArray.GetFlatData(); var numberOfZones = zones.Length; int previousPointO = -1; int previousFlatO = -1; if (timesLoaded == 0) { foreach (var point in readODData.Read()) { var o = point.O == previousPointO ? previousFlatO : zoneArray.GetFlatIndex(point.O); var d = zoneArray.GetFlatIndex(point.D); if (o >= 0 & d >= 0) { previousPointO = point.O; previousFlatO = o; var index = (o * numberOfZones + d) * NumberOfDataTypes + dataTypeOffset; data[index] = point.Data; } } } else { var iteration = timesLoaded + 1; var previousFraction = 1.0f / 2.0f; var currentFraction = 1.0f / 2.0f; foreach (var point in readODData.Read()) { var o = point.O == previousPointO ? previousFlatO : zoneArray.GetFlatIndex(point.O); var d = zoneArray.GetFlatIndex(point.D); if (o >= 0 & d >= 0) { previousPointO = point.O; previousFlatO = o; var index = (o * numberOfZones + d) * NumberOfDataTypes + dataTypeOffset; data[index] = data[index] * previousFraction + point.Data * currentFraction; } } } }
internal IZone ProduceResult(Random random, ITashaHousehold household) { var type = ClassifyHousehold(household); var homeZoneIndex = ZoneSystem.GetFlatIndex(household.HomeZone.ZoneNumber); var row = Probabilities.GetFlatData()[type][homeZoneIndex]; var pop = (float)random.NextDouble(); return(Zones[FindFirstClosestIndex(pop, row)]); }
private int PickAZoneToSelect(float pop, ITashaHousehold household, ITashaPerson person, float expansionFactor) { var type = ClassifyHousehold(household, person); var homeZoneIndex = _zoneSystem.GetFlatIndex(household.HomeZone.ZoneNumber); var row = _linkages.GetFlatData()[type][homeZoneIndex]; var pdIndex = _planningDistricts.GetFlatIndex(household.HomeZone.PlanningDistrict); float[] assigned = _assigned[pdIndex][type]; float[] emp = _totalEmployment[pdIndex][type]; var totalLinkages = GetTotalLinkages(row, assigned, emp); if (totalLinkages <= 0.0f) { Array.Copy(_originalLinkages.GetFlatData()[type][homeZoneIndex], row, row.Length); totalLinkages = VectorHelper.Sum(row, 0, row.Length); if (totalLinkages <= 0.0f) { throw new XTMFRuntimeException(this, $"A person living at zone {household.HomeZone.ZoneNumber} with worker category" + $" {type + 1} tried to find an employment zone. There was no aggregate data for any workers of this class however. Please" + $" update your worker categories and zonal residence files for this scenario!\r\n" + $"HHLD#: {household.HouseholdId}"); } } // total linkages is greater than zero pop *= totalLinkages; float acc = 0.0f; int index = 0; for (; index < row.Length; index++) { var ratio = emp[index] > 0 ? (assigned[index] / emp[index]) : 1f; acc += row[index] * Math.Max((1.0f - ratio), 0f); if (pop < acc) { break; } } // make sure it is bounded in case of rounding errors if (index == row.Length) { for (index = row.Length - 1; index >= 0; index--) { if (row[index] > 0) { break; } } // make sure we didn't run all the way back past the start of the array if (index == -1) { throw new XTMFRuntimeException(this, $"After already checking that there was an available job, none were found!"); } } _assigned[pdIndex][type][index] += expansionFactor; return(index); }
public void HouseholdIterationComplete(ITashaHousehold household, int hhldIteration, int totalHouseholdIterations) { var att = AttributeName; var toRecord = WhatToRecord; foreach (var person in household.Persons) { var exp = person.ExpansionFactor; foreach (var tripChain in person.TripChains) { if (tripChain[att] is IZone stationZone) { bool first = true; foreach (var trip in tripChain.Trips) { if (Array.IndexOf(_Modes, trip.Mode) >= 0) { if (first) { if (toRecord == ToRecord.Access || toRecord == ToRecord.AccessAndEgress) { AddToMatrix(trip.TripStartTime, exp, Zones.GetFlatIndex(trip.OriginalZone.ZoneNumber), Zones.GetFlatIndex(trip.DestinationZone.ZoneNumber), stationZone.ZoneNumber); } first = false; } else { if (toRecord == ToRecord.Egress || toRecord == ToRecord.AccessAndEgress) { AddToMatrix(trip.TripStartTime, exp, Zones.GetFlatIndex(trip.OriginalZone.ZoneNumber), Zones.GetFlatIndex(trip.DestinationZone.ZoneNumber), stationZone.ZoneNumber); } } } } } } } }
/// <summary> /// Convert the Pearson zone number into the flat spatial index for faster compute times. /// This will also load the zone system into our local cache /// </summary> private void LoadPearsonZoneNumber() { // first we are going to load in the zone system from the model system for quick reference since it is a property and would be a virtual // call every time we needed access to it, which will be often. ZoneSystem = Root.ZoneSystem.ZoneArray; PearsonFlatZoneNumber = ZoneSystem.GetFlatIndex(PearsonZoneNumber); if (PearsonZoneNumber < 0) { throw new XTMFRuntimeException("In '" + Name + "' the zone number used for Pearson is not inside of the zone system!"); } }
private void WriteEmpOccRates() { if (EmpOccRateDir == null) { return; } var results = ComputeEmpOccRates(); string dir = EmpOccRateDir; EnsureDirectory(dir); var zones = _zones.GetFlatData(); for (int emp = 0; emp < 2; emp++) { for (int occ = 0; occ < 4; occ++) { using (var writer = new StreamWriter(Path.Combine(dir, GetPrefix(emp, occ) + ".csv"))) { writer.WriteLine("Zone,Rate"); for (int i = 0; i < zones.Length; i++) { var zoneNumber = zones[i].ZoneNumber; var value = (ComputeRatesAtAPDLevel ? results[_pds.GetFlatIndex(zones[i].PlanningDistrict)] : results[i])[emp * 4 + occ]; if (value > 0.0) { writer.Write(zoneNumber); writer.Write(','); writer.WriteLine(value); } } } } } }
/// <summary> /// Copy the linkages in case they need to be reset. /// </summary> /// <param name="linkages"></param> private void CopyLinkages(SparseTriIndex <float> linkages) { _originalLinkages = linkages.CreateSimilarArray <float>(); var flatLinkages = linkages.GetFlatData(); var flatOriginal = _originalLinkages.GetFlatData(); var numberofPDs = _planningDistricts.Count; var zones = _zoneSystem.GetFlatData(); _totalEmployment = new float[numberofPDs][][]; _assigned = new float[numberofPDs][][]; for (int pd = 0; pd < numberofPDs; pd++) { _totalEmployment[pd] = new float[3][]; _assigned[pd] = new float[3][]; } for (int i = 0; i < flatLinkages.Length; i++) { for (int pd = 0; pd < numberofPDs; pd++) { _totalEmployment[pd][i] = new float[flatLinkages[i].Length]; _assigned[pd][i] = new float[flatLinkages[i].Length]; } for (int j = 0; j < flatLinkages[i].Length; j++) { Array.Copy(flatLinkages[i][j], flatOriginal[i][j], flatLinkages[i][j].Length); } } for (int type = 0; type < flatLinkages.Length; type++) { for (int i = 0; i < zones.Length; i++) { var iPD = _planningDistricts.GetFlatIndex(zones[i].PlanningDistrict); var empRow = _totalEmployment[iPD][type]; var linkRow = flatLinkages[type][i]; VectorHelper.Add(empRow, 0, empRow, 0, linkRow, 0, empRow.Length); } } }
internal IZone ProduceResult(ITashaPerson data) { ITashaHousehold household = data.Household; var homeIndex = _zoneSystem.GetFlatIndex(household.HomeZone.ZoneNumber); var type = ClassifyHousehold(household, data); var index = _index[type][homeIndex]++; var homeRow = _choices[type][homeIndex]; var ret = _zoneSystem.GetFlatData()[_choices[type][homeIndex][index]]; if (_index[type][homeIndex] >= _choices[type][homeIndex].Length) { _index[type][homeIndex] = 0; } return(ret); }
public void Execute(ITashaHousehold household, int iteration) { lock (this) { var homeZone = ZoneSystem.GetFlatIndex(household.HomeZone.ZoneNumber); foreach (var person in household.Persons) { float expansionFactor = person.ExpansionFactor; int number = (int)person.Occupation; AgeByZone.ElementAtOrDefault(person.Age)[homeZone] += expansionFactor; EmpOccResults[person.Age][Array.IndexOf(EmploymentCategories, person.EmploymentStatus)] [Array.IndexOf(OccupationCategories, person.Occupation)] += expansionFactor; if (person.Licence) { LicenceCounts[0] += expansionFactor; } else { LicenceCounts[1] += expansionFactor; } if (person.Male) { GenderCounts[0] += expansionFactor; } else { GenderCounts[1] += expansionFactor; } //var ageCategory = AgeByZone.ElementAtOrDefault(AgeCategories.IndexOf(person.Age)); //if (ageCategory != null) //{ // AgeByZone.ElementAtOrDefault(AgeCategories.IndexOf(person.Age))[homeZone] += expansionFactor; //} } if (household.Vehicles.Length >= 4) { CarCounts[4] += household.ExpansionFactor; } else { CarCounts[household.Vehicles.Length] += household.ExpansionFactor; } } }
/// <summary> /// Load the probabilities from file /// </summary> /// <param name="zoneSystem">The zone system the model is using</param> private void LoadProbabilities(SparseArray<IZone> zoneSystem) { var zones = zoneSystem.GetFlatData(); AutoProbabilities = new float[zones.Length]; TransitProbabilities = new float[zones.Length]; TotalTrips = new float[zones.Length]; using (CsvReader reader = new CsvReader(ModeSplitTruthData)) { // burn header reader.LoadLine(); // read in the rest of the data int columns; while(reader.LoadLine(out columns)) { if(columns >= 3) { int zone; reader.Get(out zone, 0); zone = zoneSystem.GetFlatIndex(zone); if(zone >= 0) { float auto, transit, totalTrips; reader.Get(out auto, 1); reader.Get(out transit, 2); reader.Get(out totalTrips, 3); AutoProbabilities[zone] = auto; TransitProbabilities[zone] = transit; TotalTrips[zone] = totalTrips; } } } } }
private void LoadData(float[] data, IReadODData<float> readODData, int dataTypeOffset, SparseArray<IZone> zoneArray, int timesLoaded) { if(readODData == null) { return; } var zones = zoneArray.GetFlatData(); var numberOfZones = zones.Length; var dataTypes = (int)DataTypes.NumberOfDataTypes; int previousPointO = -1; int previousFlatO = -1; if(timesLoaded == 0) { foreach(var point in readODData.Read()) { var o = point.O == previousPointO ? previousFlatO : zoneArray.GetFlatIndex(point.O); var d = zoneArray.GetFlatIndex(point.D); if(o >= 0 & d >= 0) { previousPointO = point.O; previousFlatO = o; var index = (o * numberOfZones + d) * dataTypes + dataTypeOffset; data[index] = point.Data; } } } else { var iteration = timesLoaded + 1; var previousFraction = 1.0f / (iteration + 1.0f); var currentFraction = iteration / (1.0f + iteration); foreach(var point in readODData.Read()) { var o = point.O == previousPointO ? previousFlatO : zoneArray.GetFlatIndex(point.O); var d = zoneArray.GetFlatIndex(point.D); if(o >= 0 & d >= 0) { previousPointO = point.O; previousFlatO = o; var index = (o * numberOfZones + d) * dataTypes + dataTypeOffset; data[index] = data[index] * previousFraction + point.Data * currentFraction; } } } }
private float[] ExtractPopulation(IDbCommand command, SparseArray<IZone> zones) { float[] populationInZone = new float[zones.GetFlatData().Length]; //Build SQL request command.CommandText = String.Format( @"SELECT [{3}].[{0}], SUM([{2}].[{1}]) FROM [{2}] INNER JOIN [{3}] ON [{2}].[{4}] = [{3}].[{4}] AND [{2}].[{5}] = [{3}].[{5}] WHERE [{2}].[{5}] = {6} AND [{3}].[{7}] = {8} GROUP BY [{3}].[{0}];", //0 ZoneNumberColumn, //1 ExpansionFactorColumnName, //2 PersonsTable, //3 HomeZoneTableName, //4 HouseholdIDColumn, //5 TTSYearColumn, //6 TTSYear, //7 ZoneSystemColumn, //8 ZoneSystemNumber ); // process data using ( var reader = command.ExecuteReader() ) { while ( reader.Read() ) { // if the zone is in our zone system add them to it var zoneNumber = reader.GetInt32( 0 ); var index = zones.GetFlatIndex( zoneNumber ); if ( index >= 0 ) { populationInZone[index] = (float)reader.GetDouble( 1 ); } } } return populationInZone; }
private int[] CreateStationIndexLookup(SparseArray<IZone> zoneSystem, IZone[] zones) { var lookup = zones.Select(z => zoneSystem.GetFlatIndex(z.ZoneNumber)).ToArray(); StationIndexLookup = lookup; return lookup; }
/// <summary> /// Save the data from the given split data to the given file as CSV. /// EmpStat, /// </summary> /// <param name="writer">The stream to write to.</param> /// <param name="splitData">The data to use</param> /// <param name="empCode">The empStat code to dump</param> private void WriteData(StreamWriter writer, SparseArray<float[]> splitData, char empCode) { var data = splitData.GetFlatData(); for ( int i = 0; i < data.Length; i++ ) { var row = splitData[i]; if ( row != null ) { // buffer as much of the header ahead of time to help performance var pdStr = string.Concat( empCode, ",", splitData.GetFlatIndex( i ), "," ); for ( int j = 0; j < row.Length; j++ ) { writer.Write( pdStr ); writer.Write( j + 1 ); writer.Write( ',' ); writer.WriteLine( row[j] ); } } } }
private void LoadProbabilities(SparseArray<IZone> zoneSystem) { var zones = zoneSystem.GetFlatData(); ObservedDistribution = new float[zones.Length]; TotalTrips = new float[zones.Length]; using (CsvReader reader = new CsvReader(ObservedDistributionFile)) { // burn header reader.LoadLine(); // read in the rest of the data int columns; while(reader.LoadLine(out columns)) { if(columns >= 2) { int zone; reader.Get(out zone, 0); zone = zoneSystem.GetFlatIndex(zone); if(zone >= 0) { float probability, totalTrips; reader.Get(out probability, 1); reader.Get(out totalTrips, 2); ObservedDistribution[zone] = probability; TotalTrips[zone] = totalTrips; } } } } }
private void FillInPopulationByZone(SparseArray<IZone> zones, int numberOfZones, IDbCommand command, float[][][] populationByAge) { for ( int j = 0; j < this.AgeSets.Count; j++ ) { populationByAge[j] = new float[this.EmploymentStatusString.Length][]; for ( int i = 0; i < this.EmploymentStatusString.Length; i++ ) { populationByAge[j][i] = new float[numberOfZones]; command.CommandText = String.Format( @"SELECT [{3}].[{0}], SUM([{2}].[{1}]) FROM [{2}] INNER JOIN [{3}] ON [{2}].[{4}] = [{3}].[{4}] AND [{2}].[{5}] = [{3}].[{5}] WHERE [{2}].[{5}] = {6} AND [{3}].[{7}] = {8} AND [{2}].[{9}] >= {10} AND [{2}].[{9}] <= {11} AND [{2}].[{13}] = '{12}' GROUP BY [{3}].[{0}];", //0 ZoneNumberColumn, //1 ExpansionFactorColumnName, //2 PersonsTable, //3 HomeZoneTableName, //4 HouseholdIDColumn, //5 TTSYearColumn, //6 TTSYear, //7 ZoneSystemColumn, //8 ZoneSystemNumber, //9 AgeColumn, //10 this.AgeSets[j].Start, //11 this.AgeSets[j].Stop, //12 EmploymentStatusString[i], //13 EmploymentStatusColumn ); using ( var reader = command.ExecuteReader() ) { while ( reader.Read() ) { var zone = reader.GetInt32( 0 ); var index = zones.GetFlatIndex( zone ); if ( index >= 0 ) { populationByAge[j][i][index] = (float)reader.GetDouble( 1 ); } } } } } }
private void ComputeFromDestination(float[][] currentTally, SparseArray<IZone> zoneArray, IZone[] zones, int m, float[][] data) { Parallel.For(0, data.Length, new ParallelOptions() { MaxDegreeOfParallelism = Environment.ProcessorCount }, delegate (int j) { for(int i = 0; i < data.Length; i++) { if(data[i] == null || data[i][j] <= 0f) continue; var choices = GetStationChoiceSplit(m, zones[i], zones[j]); if(choices == null) continue; // check for egress stations first var stationZones = choices.Item2; if(stationZones == null) { // if there are no egress stations, use the access stations stationZones = choices.Item1; } var splits = choices.Item3; var totalTrips = data[i][j]; var totalSplits = 0f; for(int z = 0; z < stationZones.Length; z++) { if(stationZones[z] != null) { totalSplits += splits[z]; } } for(int z = 0; z < stationZones.Length; z++) { if(stationZones[z] == null) break; var flatZoneNumber = zoneArray.GetFlatIndex(stationZones[z].ZoneNumber); if(currentTally[flatZoneNumber] == null) { lock (data) { System.Threading.Thread.MemoryBarrier(); if(currentTally[flatZoneNumber] == null) { currentTally[flatZoneNumber] = new float[data[i].Length]; } } } // no lock needed since we are doing it parallel in the i, so there will be no conflicts currentTally[flatZoneNumber][j] += totalTrips * (splits[z] / totalSplits); } } }); }
private void ComputeLineHaull(float[][] currentTally, SparseArray<IZone> zoneArray, IZone[] zones, int m, float[][] data) { // this can't be in parallel since we are writing to the some access and egress data entries for(int i = 0; i < data.Length; i++) { if(data[i] == null) continue; for(int j = 0; j < data[i].Length; j++) { var totalTrips = data[i][j]; if(totalTrips <= 0f) { continue; } var choices = GetStationChoiceSplit(m, zones[i], zones[j]); if(choices == null) { continue; } var accessStations = choices.Item1; var egressStations = choices.Item2; if(egressStations == null) { continue; } var splits = choices.Item3; var totalSplits = 0f; for(int z = 0; z < accessStations.Length; z++) { if(accessStations[z] != null) { totalSplits += splits[z]; } } for(int z = 0; z < accessStations.Length; z++) { if(accessStations[z] == null | egressStations[z] == null) break; var accessZoneNumber = zoneArray.GetFlatIndex(accessStations[z].ZoneNumber); var egressZoneNumber = zoneArray.GetFlatIndex(egressStations[z].ZoneNumber); // no lock needed since we are doing it parallel in the i, so there will be no conflicts currentTally[accessZoneNumber][egressZoneNumber] += totalTrips * (splits[z] / totalSplits); } } } }
private void ComputeFromOrigin(float[][] currentTally, SparseArray<IZone> zoneArray, IZone[] zones, int m, float[][] data) { Parallel.For(0, data.Length, new ParallelOptions() { MaxDegreeOfParallelism = Environment.ProcessorCount }, delegate (int i) { if(data[i] == null) return; var tallyRow = currentTally[i]; for(int j = 0; j < data[i].Length; j++) { var totalTrips = data[i][j]; if(totalTrips <= 0f) continue; var choices = GetStationChoiceSplit(m, zones[i], zones[j]); if(choices == null) continue; var stationZones = choices.Item1; var splits = choices.Item3; var totalSplits = 0f; for(int z = 0; z < stationZones.Length; z++) { if(stationZones[z] != null) { totalSplits += splits[z]; } } for(int z = 0; z < stationZones.Length; z++) { if(stationZones[z] == null) break; var flatZoneNumber = zoneArray.GetFlatIndex(stationZones[z].ZoneNumber); // no lock needed since we are doing it parallel in the i, so there will be no conflicts tallyRow[flatZoneNumber] += totalTrips * (splits[z] / totalSplits); } } }); }
private float[][][] BuildData(string[] modeNames, SparseArray<IZone> zoneSystem, SparseArray<int> regions) { var zones = zoneSystem.GetFlatData(); var modes = Root.AllModes.ToArray(); var data = new float[modes.Length][][]; var numberOfRegions = regions.GetFlatData().Length; for(int i = 0; i < data.Length; i++) { var row = data[i] = new float[numberOfRegions][]; for(int j = 0; j < row.Length; j++) { row[j] = new float[numberOfRegions]; } } using (CsvReader reader = new CsvReader(ZonalModeSplitFile)) { // burn header reader.LoadLine(); int columns; while(reader.LoadLine(out columns)) { // ignore lines without the right number of columns if(columns == 4) { string modeName; int originZone, destinationZone; float expandedPersons; reader.Get(out modeName, 0); reader.Get(out originZone, 1); reader.Get(out destinationZone, 2); reader.Get(out expandedPersons, 3); data[ModeIndex(modeName, modeNames)][regions.GetFlatIndex(zoneSystem[originZone].PlanningDistrict)][regions.GetFlatIndex(zoneSystem[destinationZone].PlanningDistrict)] += expandedPersons; } } } return data; }