public IntersectionPart Execute(IFeature other) { const string methodName = "CalculateIntersectionCommand"; IGeometry intersection; var part = new IntersectionPart(); switch (other.ShapeCopy.GeometryType) { case esriGeometryType.esriGeometryPolygon: intersection = _whole.Intersect(other.ShapeCopy, esriGeometryDimension.esriGeometry2Dimension); var area = (IArea)intersection; part.Size = Math.Abs(area.Area); part.Intersection = intersection; #if !DEBUG _logger.LogMessage(ServerLogger.msgType.infoStandard, methodName, MessageCode, string.Format("Area: {0}", area.Area)); #endif break; case esriGeometryType.esriGeometryPolyline: intersection = _whole.Intersect(other.ShapeCopy, esriGeometryDimension.esriGeometry1Dimension); var length = (IPolyline5)intersection; part.Size = Math.Abs(length.Length); part.Intersection = intersection; #if !DEBUG _logger.LogMessage(ServerLogger.msgType.infoStandard, methodName, MessageCode, string.Format("Length: {0}", length.Length)); #endif break; } return(part); }
public IntersectionPart Execute(IFeature other) { const string methodName = "CalculateMuniPrivateCommand"; var municipleIntersection = new CalculateIntersectionCommand(_whole, _logger).Execute(other); if (municipleIntersection.Intersection == null) { return(new IntersectionPart()); } var wholeMuni = (ITopologicalOperator4)municipleIntersection.Intersection; var privateFilter = new SpatialFilter { Geometry = municipleIntersection.Intersection, SpatialRel = esriSpatialRelEnum.esriSpatialRelIntersects, WhereClause = "OWNER = 'Private'" }; var cursor = LandOwnership.FeatureClass.Search(privateFilter, true); IFeature privateLand; IGeometry privateGeometry = null; while ((privateLand = cursor.NextFeature()) != null) { var intersection = wholeMuni.Intersect(privateLand.ShapeCopy, esriGeometryDimension.esriGeometry2Dimension); if (privateGeometry == null) { privateGeometry = intersection; } else { privateGeometry = ((ITopologicalOperator4)privateGeometry).Union(intersection); } } if (privateGeometry == null) { return(new IntersectionPart()); } var part = new IntersectionPart(); var area = (IArea)privateGeometry; #if !DEBUG _logger.LogMessage(ServerLogger.msgType.infoStandard, methodName, MessageCode, string.Format("Area: {0}", area.Area)); #endif part.Size = Math.Abs(area.Area); part.Intersection = privateGeometry; return(part); }
public IntersectionPart Execute(IFeature other) { const string methodName = "CalculateCountyPrivateCommand"; var countyIntersection = new CalculateIntersectionCommand(_whole, _logger).Execute(other); // out of utah if (countyIntersection.Intersection == null) { return(new IntersectionPart()); } var countyPart = (ITopologicalOperator4)countyIntersection.Intersection; var privateFilter = new SpatialFilter { Geometry = countyIntersection.Intersection, SpatialRel = esriSpatialRelEnum.esriSpatialRelIntersects, WhereClause = "OWNER = 'Private'" }; var muniFilter = new SpatialFilter { Geometry = countyIntersection.Intersection, SpatialRel = esriSpatialRelEnum.esriSpatialRelIntersects }; var privateGeometry = UnionItemsFor(LandOwnership.FeatureClass, privateFilter, countyPart); var municipalGeometry = UnionItemsFor(Municipalities.FeatureClass, muniFilter, countyPart); // no private or municipal land if (privateGeometry == null && municipalGeometry == null) { return(new IntersectionPart()); } // no municipality - return private if (municipalGeometry == null) { var privateArea = (IArea)privateGeometry; #if !DEBUG _logger.LogMessage(ServerLogger.msgType.infoStandard, methodName, MessageCode, string.Format("Area: {0}", privateArea.Area)); #endif return(new IntersectionPart { Size = Math.Abs(privateArea.Area), Intersection = privateGeometry }); } // no private - return 0 because it's places people live not in a city if (privateGeometry == null) { return(new IntersectionPart()); } // there are both private and muni var privatePart = (ITopologicalOperator4)privateGeometry; var intersection = privatePart.Difference(municipalGeometry); var part = new IntersectionPart(); var area = (IArea)intersection; #if !DEBUG _logger.LogMessage(ServerLogger.msgType.infoStandard, methodName, MessageCode, string.Format("Area: {0}", area.Area)); #endif part.Size = Math.Abs(area.Area); part.Intersection = intersection; return(part); }
public void ProcessEvent(Event nextEvent, double time) { switch (nextEvent.EventType) { case EventType.TrafficLightChange: { // Dodaj sledecu promenu semafora AddEvent(new Event(EventType.TrafficLightChange, time + 60.0)); // Dodaj dogadjaj za pesake AddEvent(new Event(EventType.StartCrossing, time)); // Dodaj dogadjaj za vozila AddEvent(new Event(EventType.EnterIntersection, time)); // Promeni svetlo na semaforu if (trafficLight == TrafficLight.EW) { trafficLight = TrafficLight.NS; } else { trafficLight = TrafficLight.EW; } } break; case EventType.Arrival: { // Uvek dodaj novi dolazak AddEvent(new Event(EventType.Arrival, time + arrival.NextValue())); TravelType traveler = travelers.NextValue(); IntersectionPart direction = intersectionPart.NextValue(); if (traveler == TravelType.Pedestrian) { // Dodaj ga u red cekanja pedestrianQue[(int)direction].Enqueue(time); // Proveri da li je novi red veci od poslednjeg najveceg if (pedestrianQue[(int)direction].Count > largestPedestrianQue) { largestPedestrianQue = pedestrianQue[(int)direction].Count; } // Zabelezi statistiku reda cekanja pedestrianQueLength[(int)direction].Add(new DoublePair(time, pedestrianQue[(int)direction].Count)); // Proveri semafor, zatim gledaj suprotne pesacke if ((int)trafficLight != (int)direction / 2) { // Dodaj dogadjaj za prelazenje AddEvent(new Event(EventType.StartCrossing, time)); } } else { // Dodaj vozila u red cekanja vehicleQue[(int)direction].Enqueue(time); // Zabelezi statistiku reda cekanja vehicleQueLength[(int)direction].Add(new DoublePair(time, vehicleQue[(int)direction].Count)); // Proveri da li je novi red veci od poslednjeg najveceg if (vehicleQue[(int)direction].Count > largestVehicleQue) { largestVehicleQue = vehicleQue[(int)direction].Count; } // Proveri semafor if ((int)trafficLight == (int)direction / 2) { if (intersectionInUse[(int)direction] == VehicleDirection.Free) { // Dodaj dogadjaj za prelazenje AddEvent(new Event(EventType.EnterIntersection, time)); } } } } break; case EventType.StartCrossing: { for (int i = 0; i < 2; i++) { // Zapad i istok su otvoreni pesacki kada je semafor za automobile sever i jug int direction = trafficLight == TrafficLight.NS ? 2 + i : i; // Pokreni sve pesake za North tj. East while (pedestrianQue[direction].Count != 0) { double timeOfArrival = pedestrianQue[direction].Dequeue(); // Zabelezi koliko je cekao pesak pedestrianWait.Add(time - timeOfArrival); // Vreme da predje double timeToCross = time + pedestrianService.NextValue(); // Dodaj dogadjaj da je pesak zavrsio prelazenje AddEvent(new Event(EventType.EndCrossing, timeToCross)); // Zauzmi pesacki peopleOnCrossing[direction]++; peopleCrossing.Add(new Tuple <double, int>(timeToCross, direction)); crossingInUse[direction] = true; } // Zabelezi da su svi pesaci prosli pedestrianQueLength[direction].Add(new DoublePair(time, 0)); } // Sortiraj pesake od najranije do najkasnijeg peopleCrossing.Sort(); } break; case EventType.EndCrossing: { // Pronadji koji prelaz je presao pesak int direction = peopleCrossing[0].Item2; // Oslobodi prelaz ako nema pesaka na njemu peopleOnCrossing[direction]--; if (peopleOnCrossing[direction] == 0) { crossingInUse[direction] = false; // Ako se oslobodio pesacki, obavesti vozila ako postoje, prvo levo iza, ako nema, onda desno iza int left = WhichWayIsLeft(direction); // Proveri da li vozilo ide desno if (intersectionInUse[left] == VehicleDirection.Right) { // Pronadji da li lokacija postoji u listi servisiranja if (vehicleCrossing.Select((t) => t.Item2).ToArray().Contains(left) == false) { AddEvent(new Event(EventType.ExitIntersection, time)); vehicleCrossing.Add(new Tuple <double, int>(time, left)); vehicleCrossing.Sort(); } } // Ako nema vozila koje skrece desno, proveri da li je ta pozicija prazna else if (intersectionInUse[left] == VehicleDirection.Free) { int right = WhichWayIsRight(direction); // Proveri da li vozilo ide levo if (intersectionInUse[right] == VehicleDirection.Left) { // Pronadji da li lokacija postoji u listi servisiranja if (vehicleCrossing.Select((t) => t.Item2).ToArray().Contains(right) == false) { AddEvent(new Event(EventType.ExitIntersection, time)); vehicleCrossing.Add(new Tuple <double, int>(time, right)); vehicleCrossing.Sort(); } } } } // Ukloni tog pesaka iz liste peopleCrossing.RemoveAt(0); } break; case EventType.EnterIntersection: { for (int i = 0; i < 2; i++) { // Sever/Jug(0) -> Sever(0), Jug(1), Istok/Zapad(1) -> Istok(2), Zapad(3) int direction = ((int)trafficLight * 2) + i; if (intersectionInUse[direction] == VehicleDirection.Free) { if (vehicleQue[direction].Count != 0) { double timeToCross = vehicleService.NextValue(); double timeOfArrival = vehicleQue[direction].Dequeue(); // Zabelezi koliko je cekao pesak vehicleWait.Add(time - timeOfArrival); // Obelezio deo raskrsnice kao zauzet intersectionInUse[direction] = vehicleDirection.NextValue(); // Zabelezi statistiku reda cekanja vehicleQueLength[(int)direction].Add(new DoublePair(time, vehicleQue[(int)direction].Count)); // Dodaj dogadjaj za izlazak iz raskrsnice AddEvent(new Event(EventType.ExitIntersection, time + timeToCross)); // Kada se desi dogadjaj za izlazak iz raskrsnice, treba da se zna koji je najraniji za izlazak vehicleCrossing.Add(new Tuple <double, int>(timeToCross, (int)direction)); vehicleCrossing.Sort(); } } } } break; case EventType.ExitIntersection: { int direction = vehicleCrossing[0].Item2; vehicleCrossing.RemoveAt(0); int across = WhichWayIsAcross(direction); // Za slucaj da se semafor promenio u medjuvremenu, // oslobodi ovaj deo raskrsnice kome je crveno svetlo, a usli su u raskrsnicu if ((int)trafficLight != direction / 2) { intersectionInUse[direction] = VehicleDirection.Free; } else { // Proveri u kom pravcu ide vozilo if (intersectionInUse[direction] == VehicleDirection.Straight) { intersectionInUse[direction] = VehicleDirection.Free; if (vehicleQue[direction].Count != 0) { AddEvent(new Event(EventType.EnterIntersection, time)); } else { if (intersectionInUse[across] == VehicleDirection.Left) { if (vehicleCrossing.Select((t) => t.Item2).ToArray().Contains(across) == false) { AddEvent(new Event(EventType.ExitIntersection, time)); vehicleCrossing.Add(new Tuple <double, int>(time, across)); vehicleCrossing.Sort(); } } } } else if (intersectionInUse[direction] == VehicleDirection.Right) { int right = WhichWayIsRight(direction); if (crossingInUse[right] == false) { intersectionInUse[direction] = VehicleDirection.Free; if (vehicleQue[direction].Count != 0) { AddEvent(new Event(EventType.EnterIntersection, time)); } else { if (intersectionInUse[across] == VehicleDirection.Left) { if (vehicleCrossing.Select((t) => t.Item2).ToArray().Contains(across) == false) { AddEvent(new Event(EventType.ExitIntersection, time)); vehicleCrossing.Add(new Tuple <double, int>(time, across)); vehicleCrossing.Sort(); } } } } } else if (intersectionInUse[direction] == VehicleDirection.Left) { int left = WhichWayIsLeft(direction); // Vozilo moze da skrene levo ako vozilo prekoputa skrece levo // ili ako je prekoputa prazno i niko ne ide u susret if ((intersectionInUse[across] == VehicleDirection.Left) || ((intersectionInUse[across] == VehicleDirection.Free) && (vehicleQue[across].Count == 0))) { if (crossingInUse[left] == false) { intersectionInUse[direction] = VehicleDirection.Free; if (vehicleQue[direction].Count != 0) { AddEvent(new Event(EventType.EnterIntersection, time)); } else { if (intersectionInUse[across] == VehicleDirection.Left) { if (vehicleCrossing.Select((t) => t.Item2).ToArray().Contains(across) == false) { AddEvent(new Event(EventType.ExitIntersection, time)); vehicleCrossing.Add(new Tuple <double, int>(time, across)); vehicleCrossing.Sort(); } } } } } } } } break; } }