private TimePeriod FitPeriodIntoOffer(OfferModel offer, TimePeriod period)
        {
            TimePeriod offerPeriod = new TimePeriod(offer.From, offer.To);
            TimePeriod printPeriod = new TimePeriod(DateTime.Today, DateTime.Today);

            if (offerPeriod.IsBefore(period) || offerPeriod.IsAfter(period))
            {
                return(null);
            }

            if (offerPeriod.HasInside(period))
            {
                printPeriod = period;
            }
            else if (offerPeriod.EndsInside(period))
            {
                printPeriod.Start = period.Start;
                printPeriod.End   = offer.To;
            }
            else if (offerPeriod.StartsInside(period))
            {
                printPeriod.Start = offer.From;
                printPeriod.End   = period.End;
            }
            else if (offerPeriod.IsInside(period))
            {
                printPeriod.Start = offer.From;
                printPeriod.End   = offer.To;
            }

            return(printPeriod);
        }
Beispiel #2
0
        private static void OfferUpdateAlgTesting()
        {
            OfferModel offer = GlobalConfig.OfferModelConection.GetAll()
                               .OrderBy(model => model.From)
                               .ToArray().First();

            TimePeriod offerPeriod = new TimePeriod(offer.From, offer.To);

            TimePeriod leftRange  = null;
            TimePeriod rightRange = null;

            if (offerPeriod.IsBefore(DateTime.Today))
            {
                leftRange  = new TimePeriod(offerPeriod.Start, offerPeriod.Start);
                rightRange = new TimePeriod(offerPeriod.End, offerPeriod.End);
            }
            else
            {
                TimePeriod[] offerPeriods = GlobalConfig.OfferModelConection.GetAll()
                                            .Select(model => new TimePeriod(model.From, model.To))
                                            .OrderBy(period => period.Start)
                                            .ToArray();
                TimePeriod[] reservedPeriods = GlobalConfig.ReservationModelConection.GetAll()
                                               .Select(model => new TimePeriod(model.From, model.To))
                                               .Where(period => offerPeriod.IntersectsWith(period))
                                               .OrderBy(period => period.Start)
                                               .ToArray();

                // Find outer limits
                DateTime leftOuterLimit  = DateTime.Today;
                DateTime rightOuterLimit = DateTime.MaxValue;
                for (int i = 0; i < offerPeriods.Length; i++)
                {
                    TimePeriod period = offerPeriods[i];
                    if (period.IsExactMatch(offerPeriod))
                    {
                        try
                        {
                            leftOuterLimit = offerPeriods[i - 1].End.AddDays(1);
                        }
                        catch (IndexOutOfRangeException)
                        {
                        }
                        try
                        {
                            rightOuterLimit = offerPeriods[i + 1].Start.AddDays(-1);
                        }
                        catch (IndexOutOfRangeException)
                        {
                        }
                        break;
                    }
                }

                DateTime leftInnerLimit  = rightOuterLimit;
                DateTime rightInnerLimit = leftOuterLimit;
                if (reservedPeriods.Length > 0)
                {
                    TimePeriod first = reservedPeriods[0];
                    TimePeriod last  = reservedPeriods[reservedPeriods.Length - 1];
                    leftInnerLimit  = first.Start < DateTime.Today ? DateTime.Today : first.Start;
                    rightInnerLimit = last.End;
                    if (offerPeriod.StartsInside(first))
                    {
                        leftInnerLimit = offerPeriod.Start;
                    }
                    if (offerPeriod.EndsInside(last))
                    {
                        rightInnerLimit = offerPeriod.End;
                    }
                }


                leftRange  = new TimePeriod(leftOuterLimit, leftInnerLimit);
                rightRange = new TimePeriod(rightInnerLimit, rightOuterLimit);
            }
            Console.WriteLine("sds");
        }
Beispiel #3
0
        private static void TimePeriodTesting()
        {
            CarModel car = GlobalConfig.CarModelConection.Get(1);

            OfferModel[] offers = GlobalConfig.OfferModelConection.GetAll();
            offers = offers.OrderBy(offer => offer.From).ToArray();
            ReservationModel[] reservations = GlobalConfig.ReservationModelConection.Filter(
                model => model.CarID == car.ID
                );
            //TimePeriod[] reservedDates = new TimePeriod[]
            //{
            //    new TimePeriod(DateTime.Today.AddDays(4),DateTime.Today.AddDays(6)),
            //    new TimePeriod(DateTime.Today,DateTime.Today.AddDays(2)),
            //    new TimePeriod(DateTime.Today.AddDays(9),DateTime.Today.AddDays(13)),
            //    new TimePeriod(DateTime.Today.AddDays(14),DateTime.Today.AddDays(19))
            //};

            List <TimePeriod> reservedDates = reservations.Select(
                reservation => new TimePeriod(reservation.From, reservation.To)
                ).OrderBy(period => period.Start).ToList();
            //reservedDates.Add(new TimePeriod(new DateTime(2019, 9, 5), new DateTime(2019, 9, 11)));
            TimePeriod range = new TimePeriod(DateTime.Today.AddDays(-2), offers.Last().To);

            TimePeriod[] freePeriods = TimePeriod.GetFreePeriods(range, reservedDates.ToArray());

            List <string> freeDatePriceOutput = new List <string>();

            foreach (OfferModel offer in offers)
            {
                TimePeriod offerPeriod = new TimePeriod(offer.From, offer.To);
                TimePeriod printPeriod = new TimePeriod(DateTime.Today, DateTime.Today);
                foreach (TimePeriod period in freePeriods)
                {
                    if (offerPeriod.IsBefore(period) || offerPeriod.IsAfter(period))
                    {
                        continue;
                    }

                    if (offerPeriod.HasInside(period))
                    {
                        printPeriod = period;
                    }
                    else if (offerPeriod.EndsInside(period))
                    {
                        printPeriod.Start = period.Start;
                        printPeriod.End   = offer.To;
                    }
                    else if (offerPeriod.StartsInside(period))
                    {
                        printPeriod.Start = offer.From;
                        printPeriod.End   = period.End;
                    }
                    else if (offerPeriod.IsInside(period))
                    {
                        printPeriod.Start = offer.From;
                        printPeriod.End   = offer.To;
                    }


                    int    days   = printPeriod.GetDaySpan() + 1;
                    double price  = days * offer.PricePerDay;
                    string output = $"{printPeriod} - price {price}";
                    freeDatePriceOutput.Add(output);
                }
            }

            Console.WriteLine("Offers");
            foreach (OfferModel offer in offers)
            {
                Console.WriteLine($"{offer.From.ToShortDateString()}-{offer.To.ToShortDateString()} price per day {offer.PricePerDay}");
            }

            Console.WriteLine("Reserved Dates");
            foreach (TimePeriod period in reservedDates)
            {
                Console.WriteLine(period);
            }

            Console.WriteLine("Free dates");
            foreach (TimePeriod period in freePeriods)
            {
                Console.WriteLine(period);
            }

            Console.WriteLine("Prices");
            foreach (string output in freeDatePriceOutput)
            {
                Console.WriteLine(output);
            }

            // for user time period input
            // check if it is in the free periods
            // find which offers corespond to that time period
            // calculate the price

            Console.WriteLine("sad");
        }
Beispiel #4
0
        private void FindUpdateLimits()
        {
            /*
             *  Algorithm needs to find how much given period can expand or shrink depending on other periods.
             *  First it checks how much it can expand by checking other offer periods.
             *  Then it checks how much it can shrink by checking reservations for that offer.
             *  Then it creates left and right range as available update values.
             */
            TimePeriod offerPeriod = new TimePeriod(selectedOffer.Record.From, selectedOffer.Record.To);


            /*
             * If the selected offer is in the past, there is no point in updating it.
             */
            if (offerPeriod.IsBefore(DateTime.Today))
            {
                leftRange  = null;
                rightRange = null;
                return;
            }

            // find reservations for this offer period
            TimePeriod[] reservationPeriods = RentACarLibrary.GlobalConfig.ReservationModelConection
                                              .Filter(model => model.CarID == (view.Car as CarModel).ID)
                                              .Select(model => new TimePeriod(model.From, model.To))
                                              .Where(period => offerPeriod.IntersectsWith(period))
                                              .OrderBy(period => period.Start)
                                              .ToArray();

            // find offers for the selected offer's car
            TimePeriod[] offerPeriods = RentACarLibrary.GlobalConfig.OfferModelConection
                                        .Filter(model => model.CarID == selectedOffer.Record.CarID)
                                        .Select(model => new TimePeriod(model.From, model.To))
                                        .OrderBy(period => period.Start)
                                        .ToArray();

            /*
             *  The minimum value that the left outer limit can take is the present day.
             *  There is no point in expanding the time period so it starts in the past.
             *  And if the period already starts in the past, we won't be able to expand or shrink
             *  it on the left side.
             */
            // Find outer limits
            DateTime leftOuterLimit  = (offerPeriod.Start < DateTime.Today) ? offerPeriod.Start : DateTime.Today;
            DateTime rightOuterLimit = DateTime.MaxValue;

            for (int i = 0; i < offerPeriods.Length; i++)
            {
                TimePeriod period = offerPeriods[i];
                if (period.IsExactMatch(offerPeriod))
                {
                    // offer before
                    try
                    {
                        // ignore offers that are in the past
                        if (!offerPeriods[i - 1].IsBefore(DateTime.Today))
                        {
                            leftOuterLimit = offerPeriods[i - 1].End.AddDays(1);
                        }
                    }
                    catch (IndexOutOfRangeException)
                    {
                    }
                    // offer after
                    try
                    {
                        rightOuterLimit = offerPeriods[i + 1].Start.AddDays(-1);
                    }
                    catch (IndexOutOfRangeException)
                    {
                    }
                    break;
                }
            }

            // Find Inner limits
            // asumption that offer has no active reservations
            DateTime leftInnerLimit  = rightOuterLimit;
            DateTime rightInnerLimit = leftOuterLimit;

            // then check against that asumption
            if (reservationPeriods.Length > 0)
            {
                TimePeriod firstReservation = reservationPeriods.First();
                TimePeriod lastReservation  = reservationPeriods.Last();
                // Again checks if the start should not change at all because it is already in the past.
                leftInnerLimit  = firstReservation.Start < DateTime.Today ? offerPeriod.Start : firstReservation.Start;
                rightInnerLimit = lastReservation.End;

                // Here we check for reservations that may contain more than one offer
                if (offerPeriod.StartsInside(firstReservation))
                {
                    // First reservation began in an offer before the selected offer
                    leftInnerLimit = offerPeriod.Start;
                }
                if (offerPeriod.EndsInside(lastReservation))
                {
                    // Last reservation ends in an offer after the selected offer
                    rightInnerLimit = offerPeriod.End;
                }
            }

            leftRange  = new TimePeriod(leftOuterLimit, leftInnerLimit);
            rightRange = new TimePeriod(rightInnerLimit, rightOuterLimit);
        }