private void DistributePopulation(DemographicCategoryGeneration cat, float[] ageProbability, float[][] assignedPersons, int catIndex, float[][] ret) { var timeOfDayRate = CurrentTimeOfDayRates.GiveData(); var dailyRates = CurrentDailyRates.GiveData(); var zones = Root.ZoneSystem.ZoneArray.GetFlatData(); var numberOfMobilityTypes = GetMobilityTypeTotal(); var currentMobilityType = catIndex % numberOfMobilityTypes; ModeSplit.StartNewInteractiveModeSplit(NumberOfGenerations); // Setup the mode choice function, since each zone is the same, we only need to do this once cat.InitializeDemographicCategory(); var age = cat.AgeCategoryRange[0].Start; //ageOfffset = foreach each OD Pair, for each mobility category multiplied by the age - 2 (workrs start at 2). var ageOffset = (5 * zones.Length * zones.Length) * (age - 2); // for each origin zone Parallel.For(0, zones.Length, i => { var pdI = zones[i].PlanningDistrict; // Offset of the origin var iOffset = i * zones.Length * numberOfMobilityTypes; // offset by the age category plus the mobility category offset iOffset += ageOffset + currentMobilityType * zones.Length; // for each destination var row = ret[i]; var assignedPersonRow = assignedPersons[i]; if (ageProbability[i] == 0) { for (int j = 0; j < zones.Length; j++) { row[j] = 0; } } else { int currentJIndex = 0; for (int j = 0; j < zones.Length; j++) { if (assignedPersonRow[j] <= 0) { row[j] = 0; } else if (j == i) { throw new XTMFRuntimeException(this, "We found assigned persons for an intra-zonal work trip!"); } else { var pdJ = zones[j].PlanningDistrict; // compute the mode choice var util = ModeSplit.ComputeUtility(zones[i], zones[j]); if (float.IsNaN(util) | float.IsInfinity(util)) { throw new XTMFRuntimeException(this, "We came across an invalid utility! Age = " + age + " origin = " + zones[i].ZoneNumber + " destination = " + zones[j].ZoneNumber + " demographic category = '" + cat.ToString() + "'"); } // Process how many persons go here // probabilities contains the probability of being in that age category already var rate = timeOfDayRate[pdI, pdJ, age] * dailyRates[pdI, pdJ, age]; var persons = ageProbability[i] * assignedPersonRow[j]; if ((rate == 0) & (persons > 0)) { throw new XTMFRuntimeException(this, "We lost generation for " + zones[i].ZoneNumber + " to " + zones[j].ZoneNumber + ". " + persons + " persons in category " + catIndex + "."); } row[j] = persons * rate * MobilityCache[iOffset + currentJIndex]; } currentJIndex++; } } }); }
private void DistributePopulation(DemographicCategoryGeneration cat, float[] ageProbability, float[][] assignedPersons, int catIndex, float[][] ret) { var timeOfDayRate = this.CurrentTimeOfDayRates.GiveData(); var dailyRates = this.CurrentDailyRates.GiveData(); var zones = this.Root.ZoneSystem.ZoneArray.GetFlatData(); var numberOfMobilityTypes = GetMobilityTypeTotal(); var currentMobilityType = catIndex % numberOfMobilityTypes; this.ModeSplit.StartNewInteractiveModeSplit( this.NumberOfGenerations ); // Setup the mode choice function, since each zone is the same, we only need to do this once cat.InitializeDemographicCategory(); var age = cat.AgeCategoryRange[0].Start; //ageOfffset = foreach each OD Pair, for each mobility category multiplied by the age - 2 (workrs start at 2). var ageOffset = ( 5 * zones.Length * zones.Length ) * ( age - 2 ); // for each origin zone Parallel.For( 0, zones.Length, (int i) => { var pdI = zones[i].PlanningDistrict; // Offset of the origin var iOffset = i * zones.Length * numberOfMobilityTypes; // offset by the age category plus the mobility category offset iOffset += ageOffset + currentMobilityType * zones.Length; // for each destination var row = ret[i]; var assignedPersonRow = assignedPersons[i]; if ( ageProbability[i] == 0 ) { for ( int j = 0; j < zones.Length; j++ ) { row[j] = 0; } } else { int currentJIndex = 0; for ( int j = 0; j < zones.Length; j++ ) { if ( assignedPersonRow[j] <= 0 ) { row[j] = 0; } else if ( j == i ) { throw new XTMFRuntimeException( "We found assigned persons for an intra-zonal work trip!" ); } else { var pdJ = zones[j].PlanningDistrict; // compute the mode choice var util = this.ModeSplit.ComputeUtility( zones[i], zones[j] ); if ( float.IsNaN( util ) | float.IsInfinity( util ) ) { throw new XTMFRuntimeException( "We came across an invalid utility! Age = " + age + " origin = " + zones[i].ZoneNumber + " destination = " + zones[j].ZoneNumber + " demographic category = '" + cat.ToString() + "'" ); } // Process how many persons go here // probabilities contains the probability of being in that age category already var rate = timeOfDayRate[pdI, pdJ, age] * dailyRates[pdI, pdJ, age]; var persons = ageProbability[i] * assignedPersonRow[j]; if ( ( rate == 0 ) & ( persons > 0 ) ) { throw new XTMFRuntimeException( "We lost generation for " + zones[i].ZoneNumber + " to " + zones[j].ZoneNumber + ". " + persons + " persons in category " + catIndex + "." ); } row[j] = persons * rate * this.MobilityCache[iOffset + currentJIndex]; } currentJIndex++; } } } ); }