public void SetUtilities(ISampleItem sampleItem, int sampleFrequency) { if (sampleItem == null) { throw new ArgumentNullException("sampleItem"); } ChoiceProbabilityCalculator.Alternative alternative = sampleItem.Alternative; IHouseholdWrapper household = _tour.Household; IPersonWrapper person = _tour.Person; IPersonDayWrapper personDay = _tour.PersonDay; // var householdHasChildren = household.HasChildren; IParcelWrapper destinationParcel = ChoiceModelFactory.Parcels[sampleItem.ParcelId]; IParcelWrapper excludedParcel = person.UsualWorkParcel == null || person.UsualWorkParcelId == household.ResidenceParcelId || _tour.DestinationPurpose != Global.Settings.Purposes.Work || _tour.GetTourCategory() == Global.Settings.TourCategories.WorkBased ? null : person.UsualWorkParcel; bool usualWorkParcel = (excludedParcel != null && excludedParcel.Id == destinationParcel.Id); // only 1 for oddball alternative on tours with oddball alternative int usualWorkParcelFlag = usualWorkParcel.ToFlag(); // Comment out these nesting calls when estimating the conditional flat model // model is NL with oddball alternative if (usualWorkParcelFlag == 0) { // this alternative is in the non-oddball nest alternative.AddNestedAlternative(_sampleSize + 2, 0, 60); // associates alternative with non-oddball nest } else { // this is the oddball alternative alternative.AddNestedAlternative(_sampleSize + 3, 1, 60); // associates alternative with oddball nest } if (!alternative.Available) { return; } // use this block of code to eliminate the oddball alternative for estimation of the conditional model //if (usualWorkParcelFlag == 1) { // alternative.Available = false; // // return; //} double fastestTravelTime = ImpedanceRoster.GetValue("ivtime", Global.Settings.Modes.Hov3, Global.Settings.PathTypes.FullNetwork, Global.Settings.ValueOfTimes.DefaultVot, _fastestAvailableTimeOfDay, _tour.OriginParcel, destinationParcel).Variable + ImpedanceRoster.GetValue("ivtime", Global.Settings.Modes.Hov3, Global.Settings.PathTypes.FullNetwork, Global.Settings.ValueOfTimes.DefaultVot, _fastestAvailableTimeOfDay, destinationParcel, _tour.OriginParcel).Variable; if (fastestTravelTime >= _maxAvailableMinutes) { alternative.Available = false; return; } alternative.Choice = destinationParcel; double tourLogsum; if (_tour.IsHomeBasedTour) { ChoiceProbabilityCalculator.Alternative nestedAlternative = Global.ChoiceModelSession.Get <WorkTourModeModel>().RunNested(_tour, destinationParcel, household.VehiclesAvailable, person.GetTransitFareDiscountFraction()); tourLogsum = nestedAlternative == null ? 0 : nestedAlternative.ComputeLogsum(); } else { ChoiceProbabilityCalculator.Alternative nestedAlternative = Global.ChoiceModelSession.Get <WorkBasedSubtourModeModel>().RunNested(_tour, destinationParcel); tourLogsum = nestedAlternative == null ? 0 : nestedAlternative.ComputeLogsum(); } //var purpose = _tour.TourPurposeSegment; //var nonWorkPurpose = _tour.DestinationPurpose != Global.Settings.Purposes.Work; int carOwnership = person.GetCarOwnershipSegment(); //var votSegment = _tour.VotALSegment; //var transitAccess = destinationParcel.TransitAccessSegment(); //var aggregateLogsum = Global.AggregateLogsums[destinationParcel.ZoneId][purpose][carOwnership][votSegment][transitAccess]; //var aggregateLogsumHomeBased = Global.AggregateLogsums[destinationParcel.ZoneId][Global.Settings.Purposes.HomeBasedComposite][carOwnership][votSegment][transitAccess]; //var aggregateLogsumWorkBased = Global.AggregateLogsums[destinationParcel.ZoneId][Global.Settings.Purposes.Work_BASED][carOwnership][votSegment][transitAccess]; double distanceFromOrigin = _tour.OriginParcel.DistanceFromOrigin(destinationParcel, _tour.DestinationArrivalTime); // var distanceFromOrigin0 = Math.Max(0, Math.Min(distanceFromOrigin - .5, 1 - .5)); // var distanceFromOrigin3 = Math.Max(0, distanceFromOrigin - 1); // var distanceFromOrigin4 = Math.Min(distanceFromOrigin, .10); // var distanceFromOrigin5 = Math.Max(0, Math.Min(distanceFromOrigin - .1, .5 - .1)); // var distanceFromOrigin8 = Math.Max(0, Math.Min(distanceFromOrigin - .1, .35 - .1)); // var distanceFromOrigin9 = Math.Max(0, Math.Min(distanceFromOrigin - .35, 1 - .35)); double distanceFromOriginLog = Math.Log(1 + distanceFromOrigin); double distanceFromWorkLog = person.UsualWorkParcel.DistanceFromWorkLog(destinationParcel, 1); double distanceFromSchoolLog = person.UsualSchoolParcel.DistanceFromSchoolLog(destinationParcel, 1); // var millionsSquareFeet = destinationZoneTotals.MillionsSquareFeet(); double timePressure = Math.Log(1 - fastestTravelTime / _maxAvailableMinutes); // log transforms of buffers for Neighborhood effects double empEduBuffer = Math.Log(destinationParcel.EmploymentEducationBuffer1 + 1.0); // var EMPFOO_B = Math.Log(destinationParcel.EmploymentFoodBuffer1 + 1.0); // var EMPGOV_B = Math.Log(destinationParcel.EmploymentGovernmentBuffer1 + 1.0); double empOfcBuffer = Math.Log(destinationParcel.EmploymentOfficeBuffer1 + 1.0); // var EMPRET_B = Math.Log(destinationParcel.EmploymentRetailBuffer1 + 1.0); // var EMPSVC_B = Math.Log(destinationParcel.EmploymentServiceBuffer1 + 1.0); // var EMPMED_B = Math.Log(destinationParcel.EmploymentMedicalBuffer1 + 1.0); double empIndBuffer = Math.Log(destinationParcel.EmploymentIndustrialBuffer1 + destinationParcel.EmploymentAgricultureConstructionBuffer1 + 1.0); // var EMPTOT_B = Math.Log(destinationParcel.EmploymentTotalBuffer1 + 1.0); double housesBuffer = Math.Log(destinationParcel.HouseholdsBuffer1 + 1.0); // var STUDK12B = Math.Log(destinationParcel.StudentsK8Buffer1 + destinationParcel.StudentsHighSchoolBuffer1 + 1.0); // var STUDUNIB = Math.Log(destinationParcel.StudentsUniversityBuffer1 + 1.0); // var EMPHOU_B = Math.Log(destinationParcel.EmploymentTotalBuffer1 + destinationParcel.HouseholdsBuffer1 + 1.0); // parking attributes // var parcelParkingDensity = destinationParcel.ParcelParkingPerTotalEmployment(); // var zoneParkingDensity = destinationParcel.ZoneParkingPerTotalEmploymentAndK12UniversityStudents(destinationZoneTotals, millionsSquareFeet); // var ParkingPaidDailyLogBuffer1 = Math.Log(1 + destinationParcel.ParkingOffStreetPaidDailySpacesBuffer1); // connectivity attributes // var c34Ratio = destinationParcel.C34RatioBuffer1(); // var carDeficitFlag = FlagUtility.GetCarDeficitFlag(carOwnership); // includes no cars // var carCompetitionFlag = FlagUtility.GetCarCompetitionFlag(carOwnership); // exludes no cars int noCarCompetitionFlag = FlagUtility.GetNoCarCompetitionFlag(carOwnership); // var noCarsFlag = FlagUtility.GetNoCarsFlag(carOwnership); // Usual location attributes alternative.AddUtilityTerm(1, usualWorkParcelFlag); alternative.AddUtilityTerm(2, person.IsPartTimeWorker.ToFlag() * usualWorkParcelFlag); alternative.AddUtilityTerm(3, person.IsStudentAge.ToFlag() * usualWorkParcelFlag); alternative.AddUtilityTerm(4, _primaryFlag * personDay.TwoOrMoreWorkToursExist().ToFlag() * usualWorkParcelFlag); alternative.AddUtilityTerm(5, personDay.WorkStopsExist().ToFlag() * usualWorkParcelFlag); alternative.AddUtilityTerm(6, _secondaryFlag * usualWorkParcelFlag); // non-usual location attributes alternative.AddUtilityTerm(11, (!usualWorkParcel).ToFlag() * sampleItem.AdjustmentFactor); alternative.AddUtilityTerm(12, _tour.IsHomeBasedTour.ToFlag() * (!usualWorkParcel).ToFlag() * timePressure); alternative.AddUtilityTerm(13, (!usualWorkParcel).ToFlag() * person.IsFulltimeWorker.ToFlag() * tourLogsum); alternative.AddUtilityTerm(14, (!usualWorkParcel).ToFlag() * person.IsPartTimeWorker.ToFlag() * tourLogsum); alternative.AddUtilityTerm(15, (!usualWorkParcel).ToFlag() * person.IsNotFullOrPartTimeWorker.ToFlag() * tourLogsum); alternative.AddUtilityTerm(16, (!usualWorkParcel).ToFlag() * person.IsRetiredAdult.ToFlag() * distanceFromOriginLog); alternative.AddUtilityTerm(17, (!usualWorkParcel).ToFlag() * distanceFromWorkLog); alternative.AddUtilityTerm(18, (!usualWorkParcel).ToFlag() * person.IsStudentAge.ToFlag() * distanceFromSchoolLog); alternative.AddUtilityTerm(19, (!usualWorkParcel).ToFlag() * noCarCompetitionFlag * destinationParcel.ParkingHourlyEmploymentCommercialMixBuffer1()); // non-usual location Neighborhood attributes alternative.AddUtilityTerm(31, (!usualWorkParcel).ToFlag() * empEduBuffer); alternative.AddUtilityTerm(32, (!usualWorkParcel).ToFlag() * empOfcBuffer); alternative.AddUtilityTerm(33, (!usualWorkParcel).ToFlag() * housesBuffer); alternative.AddUtilityTerm(34, (!usualWorkParcel).ToFlag() * empIndBuffer); // non-usual location Size terms (consider conditioning these by fulltime, parttime, notFTPT, an income (see original sacog spec) alternative.AddUtilityTerm(40, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentEducation); alternative.AddUtilityTerm(41, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentFood); alternative.AddUtilityTerm(42, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentGovernment); alternative.AddUtilityTerm(43, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentOffice); alternative.AddUtilityTerm(44, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentRetail); alternative.AddUtilityTerm(45, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentService); alternative.AddUtilityTerm(46, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentMedical); alternative.AddUtilityTerm(47, (!usualWorkParcel).ToFlag() * destinationParcel.EmploymentIndustrial + destinationParcel.EmploymentAgricultureConstruction); alternative.AddUtilityTerm(48, (!usualWorkParcel).ToFlag() * destinationParcel.Households); alternative.AddUtilityTerm(49, (!usualWorkParcel).ToFlag() * destinationParcel.StudentsUniversity); // OD shadow pricing if (!usualWorkParcel && Global.Configuration.ShouldUseODShadowPricing) { int ori = _tour.OriginParcel.District; int des = destinationParcel.District; //var first = res <= des? res : des; //var second = res <= des? des : res; double shadowPriceConfigurationParameter = ori == des ? Global.Configuration.WorkTourDestinationOOShadowPriceCoefficient : Global.Configuration.WorkTourDestinationODShadowPriceCoefficient; int odShadowPriceF12Value = MAX_REGULAR_PARAMETER + Global.Configuration.NumberOfODShadowPricingDistricts * (ori - 1) + des; alternative.AddUtilityTerm(odShadowPriceF12Value, shadowPriceConfigurationParameter); } // // usual location size term // alternative.AddUtilityTerm(50, usualWorkParcelFlag * 1); // // Comment out these nesting calls when estimating the conditional flat model // // model is NL with oddball alternative // if (usualWorkParcelFlag == 0) { // // this alternative is in the non-oddball nest // alternative.AddNestedAlternative(_sampleSize + 2, 0, 60); // associates alternative with non-oddball nest // } // else { // // this is the oddball alternative // alternative.AddNestedAlternative(_sampleSize + 3, 1, 60); // associates alternative with oddball nest // } }