patterncsharpMinor
Finding the busiest time-frame in a parking lot
Viewed 0 times
thetimelotfindingbusiestframeparking
Problem
The text file containing cars' arrival and departure time will upload stuff from the parking lot.
Text will be like this:
I created a
The method that parses the text file, fills into
I wrote the method shown below to find the busiest time-frame and how many cars were in the parking lot. I'm not sure if this is an effective way to do that:
```
public static ParkTimeframe getPickTimeframe(List cars)
{
List timeFrames = new List();
DateTime dtStart = cars.First().arrivalTime;
DateTime dtEnd = cars.First().leavingTime;
int count = 0;
foreach (ParkedCar car in
Text will be like this:
10:10, 11:10
10:30, 12:40
10:25, 11:10
11:10, 12:20I created a
ParkedCar class:public class ParkerCar
{
public DateTime ArrivalTime { get; set; }
public DateTime DepartureTime { get; set; }
}The method that parses the text file, fills into
List, and sorts them by the cars' arrival time:public class ParkingLotRepository
{
public List getParkedCars()
{
List parkedCars = new List();
foreach (string line in File.ReadLines(path))
{
string[] times = line.Split(',');
bool isValid = true;
DateTime dtStart;
if (!DateTime.TryParseExact(times[0].Trim(), "HH:mm",
CultureInfo.InvariantCulture,
DateTimeStyles.NoCurrentDateDefault, out dtStart))
isValid = false;
DateTime dtEnd;
if (!DateTime.TryParseExact(times[1].Trim(), "HH:mm",
CultureInfo.InvariantCulture,
DateTimeStyles.NoCurrentDateDefault, out dtEnd))
isValid = false;
if (isValid)
{
parkedCars.Add(new ParkedCar
{
ArrivalTime = dtStart,
DepartureTime = dtEnd
});
}
}
parkedCars = parkedCars
.OrderBy(c => c.ArrivalTime)
.ThenBy(c => c.DepartureTime)
.ToList();
return parkedCars;
}
}I wrote the method shown below to find the busiest time-frame and how many cars were in the parking lot. I'm not sure if this is an effective way to do that:
```
public static ParkTimeframe getPickTimeframe(List cars)
{
List timeFrames = new List();
DateTime dtStart = cars.First().arrivalTime;
DateTime dtEnd = cars.First().leavingTime;
int count = 0;
foreach (ParkedCar car in
Solution
Naming Conventions
MSDN, General Naming Conventions
-
DO NOT use Hungarian notation:
-
DO favor readability over brevity:
MSDN, Naming Guidelines / Capitalization Conventions
-
DO use PascalCasing for all public member, type, and namespace names consisting of multiple words:
Implementation
Your current implementation, besides efficiency, is not working correctly.
For parkings as the following:
It should output
However, it outputs:
Here are my changes to the code, calculating the correct peak time frame, only assuming the
And here is the code to test it:
```
public static void Main()
{
Console.WriteLine("Enter to start..");
Console.ReadLine();
// Parking opens at 07:00
DateTime parkingOpenDate = DateTime.Now.Date.AddHours(7);
List parkingLogs = new List
(
// t --xxxxxxxx--------------------------------07:02 - 07:10
// t ---xxxxxxxx-------------------------------07:03 -
MSDN, General Naming Conventions
-
DO NOT use Hungarian notation:
- [dt]Start in
getPickTimeframe()-->DateTime currentFrameStartDate
- [dt]End in
getPickTimeframe()-->DateTime currentFrameEndDate
-
DO favor readability over brevity:
ParkedCar-->ParkingLog
getPickTimeframe(List [cars])-->GetPeakTimeFrame(List parkingLogs)
public int [countCars];-->public int TotalNumberOfParkedCars;
int [count] = 0;-->int currentFrameNumberOfParkedCars;
MSDN, Naming Guidelines / Capitalization Conventions
-
DO use PascalCasing for all public member, type, and namespace names consisting of multiple words:
- [G]et[Pick]Time[F]rame() -->
GetPeakTimeFrame()
- class ParkTime[F]rame
- ParkTime[F]rame.[S]tartTime
- ParkTime[F]rame.[E]ndTime
- ParkTime[F]rame.[C]ountCars --> Also see above for alternative name
- ParkedCar.[A]rrivalTime
- ParkedCar.[L]eavingTime
Implementation
Your current implementation, besides efficiency, is not working correctly.
For parkings as the following:
// Parking opens at 07:00
DateTime parkingOpenDate = DateTime.Now.Date.AddHours(7);
// t --xxxxxxxx--------------------------------07:02 - 07:10
// t ---xxxxxxxx-------------------------------07:03 - 07:11
// t --------------xxxxxxxx--------------------07:14 - 07:22
// t --------xxxxxxxxx-------------------------07:08 - 07:17
// t 001222223321112221111100000000000000000000
new ParkingLog[]
{
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(2), LeavingTime = parkingOpenDate.AddMinutes(10) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(3), LeavingTime = parkingOpenDate.AddMinutes(11) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(14), LeavingTime = parkingOpenDate.AddMinutes(22) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(8), LeavingTime = parkingOpenDate.AddMinutes(17) }
}It should output
07:08.00 - 07:10:00 with 3 carsHowever, it outputs:
07:02.00 - 07:10:00 with 2 carsHere are my changes to the code, calculating the correct peak time frame, only assuming the
LeavingDate of each ParkingLog (ParkedCar in your source) is greater than the ArrivalDate:public class _113182
{
private SortedList carParkCapacityTracker = new SortedList();
public class ParkingTimeFrame
{
public DateTime StartTime { get; set; }
public DateTime EndTime { get; set; }
public int TotalNumberOfParkedCars { get; set; }
public override string ToString()
{
return string.Format("{0:HH:mm.ss} - {1:HH:mm:ss} | #Cars: {2}", StartTime, EndTime, TotalNumberOfParkedCars);
}
}
public class ParkingLog
{
public DateTime ArrivalTime { get; set; }
public DateTime LeavingTime { get; set; }
public override string ToString()
{
return string.Format("{0:HH:mm:ss} - {1:HH:mm:ss}", ArrivalTime, LeavingTime);
}
}
private void TrackCarParkingAction(DateTime actionDate, int actionEffect)
{
if (!carParkCapacityTracker.ContainsKey(actionDate))
{
carParkCapacityTracker.Add(actionDate, actionEffect);
}
else
{
carParkCapacityTracker[actionDate] += actionEffect;
}
}
private void TrackCarParkingAction(ParkingLog parkingLog)
{
TrackCarParkingAction(parkingLog.ArrivalTime, +1);
TrackCarParkingAction(parkingLog.LeavingTime, -1);
}
public ParkingTimeFrame GetPeakTimeFrame(List parkingLogs)
{
carParkCapacityTracker.Clear();
parkingLogs.ForEach(TrackCarParkingAction);
int currentNumberOfParkedCars = 0;
int maximumNumberOfParkedCars = 0;
int maximumCapacityFrameOffset = 0;
for (int currentFrameOffset = 0; currentFrameOffset < carParkCapacityTracker.Count; currentFrameOffset++)
{
currentNumberOfParkedCars += carParkCapacityTracker.Values[currentFrameOffset];
if (maximumNumberOfParkedCars <= currentNumberOfParkedCars)
{
maximumNumberOfParkedCars = currentNumberOfParkedCars;
maximumCapacityFrameOffset = currentFrameOffset;
}
}
return new ParkingTimeFrame()
{
StartTime = carParkCapacityTracker.Keys[maximumCapacityFrameOffset],
EndTime = carParkCapacityTracker.Keys[maximumCapacityFrameOffset + 1],
TotalNumberOfParkedCars = maximumNumberOfParkedCars
};
}
}And here is the code to test it:
```
public static void Main()
{
Console.WriteLine("Enter to start..");
Console.ReadLine();
// Parking opens at 07:00
DateTime parkingOpenDate = DateTime.Now.Date.AddHours(7);
List parkingLogs = new List
(
// t --xxxxxxxx--------------------------------07:02 - 07:10
// t ---xxxxxxxx-------------------------------07:03 -
Code Snippets
// Parking opens at 07:00
DateTime parkingOpenDate = DateTime.Now.Date.AddHours(7);
// t --xxxxxxxx--------------------------------07:02 - 07:10
// t ---xxxxxxxx-------------------------------07:03 - 07:11
// t --------------xxxxxxxx--------------------07:14 - 07:22
// t --------xxxxxxxxx-------------------------07:08 - 07:17
// t 001222223321112221111100000000000000000000
new ParkingLog[]
{
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(2), LeavingTime = parkingOpenDate.AddMinutes(10) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(3), LeavingTime = parkingOpenDate.AddMinutes(11) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(14), LeavingTime = parkingOpenDate.AddMinutes(22) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(8), LeavingTime = parkingOpenDate.AddMinutes(17) }
}07:08.00 - 07:10:00 with 3 cars07:02.00 - 07:10:00 with 2 carspublic class _113182
{
private SortedList<DateTime, int> carParkCapacityTracker = new SortedList<DateTime, int>();
public class ParkingTimeFrame
{
public DateTime StartTime { get; set; }
public DateTime EndTime { get; set; }
public int TotalNumberOfParkedCars { get; set; }
public override string ToString()
{
return string.Format("{0:HH:mm.ss} - {1:HH:mm:ss} | #Cars: {2}", StartTime, EndTime, TotalNumberOfParkedCars);
}
}
public class ParkingLog
{
public DateTime ArrivalTime { get; set; }
public DateTime LeavingTime { get; set; }
public override string ToString()
{
return string.Format("{0:HH:mm:ss} - {1:HH:mm:ss}", ArrivalTime, LeavingTime);
}
}
private void TrackCarParkingAction(DateTime actionDate, int actionEffect)
{
if (!carParkCapacityTracker.ContainsKey(actionDate))
{
carParkCapacityTracker.Add(actionDate, actionEffect);
}
else
{
carParkCapacityTracker[actionDate] += actionEffect;
}
}
private void TrackCarParkingAction(ParkingLog parkingLog)
{
TrackCarParkingAction(parkingLog.ArrivalTime, +1);
TrackCarParkingAction(parkingLog.LeavingTime, -1);
}
public ParkingTimeFrame GetPeakTimeFrame(List<ParkingLog> parkingLogs)
{
carParkCapacityTracker.Clear();
parkingLogs.ForEach(TrackCarParkingAction);
int currentNumberOfParkedCars = 0;
int maximumNumberOfParkedCars = 0;
int maximumCapacityFrameOffset = 0;
for (int currentFrameOffset = 0; currentFrameOffset < carParkCapacityTracker.Count; currentFrameOffset++)
{
currentNumberOfParkedCars += carParkCapacityTracker.Values[currentFrameOffset];
if (maximumNumberOfParkedCars <= currentNumberOfParkedCars)
{
maximumNumberOfParkedCars = currentNumberOfParkedCars;
maximumCapacityFrameOffset = currentFrameOffset;
}
}
return new ParkingTimeFrame()
{
StartTime = carParkCapacityTracker.Keys[maximumCapacityFrameOffset],
EndTime = carParkCapacityTracker.Keys[maximumCapacityFrameOffset + 1],
TotalNumberOfParkedCars = maximumNumberOfParkedCars
};
}
}public static void Main()
{
Console.WriteLine("Enter to start..");
Console.ReadLine();
// Parking opens at 07:00
DateTime parkingOpenDate = DateTime.Now.Date.AddHours(7);
List<ParkingLog> parkingLogs = new List<ParkingLog>
(
// t --xxxxxxxx--------------------------------07:02 - 07:10
// t ---xxxxxxxx-------------------------------07:03 - 07:11
// t --------------xxxxxxxx--------------------07:14 - 07:22
// t --------xxxxxxxxx-------------------------07:08 - 07:17
// t 001222223321112221111100000000000000000000
new ParkingLog[]
{
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(2), LeavingTime = parkingOpenDate.AddMinutes(10) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(3), LeavingTime = parkingOpenDate.AddMinutes(11) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(14), LeavingTime = parkingOpenDate.AddMinutes(22) },
new ParkingLog() { ArrivalTime = parkingOpenDate.AddMinutes(8), LeavingTime = parkingOpenDate.AddMinutes(17) }
}
);
// Should output 07:08 - 07:10 with 3 cars
Console.WriteLine("{0}", new _113182().GetPeakTimeFrame(parkingLogs));
}Context
StackExchange Code Review Q#113182, answer score: 7
Revisions (0)
No revisions yet.