/// <summary> /// Cook one round of the specified menu /// </summary> /// <param name="menu">Menu to cook a round from</param> /// <param name="itemsReady">Counter of items with entire quantity already cooked</param> /// <returns>string summarizing the round cooking results</returns> private string CookRound(GrillMenuModel menu, ref int itemsReady) { int grillAvailableArea = GrillLength * GrillWidth; string roundSummary = ""; // Items Check foreach (var item in menu.Items.OrderBy(i => i.Length * i.Width)) { if (item.Quantity != 0) { int itemArea = Convert.ToInt16(Math.Truncate((double)(item.Length.Value * item.Width.Value))); if (itemArea <= grillAvailableArea) { int itemsFitting = grillAvailableArea / itemArea; itemsFitting = (itemsFitting > item.Quantity) ? item.Quantity.Value : itemsFitting; //Update info grillAvailableArea -= itemArea * itemsFitting; item.Quantity -= itemsFitting; if (itemsFitting != 0) { roundSummary += string.Format("'{0}' x {1} | ", item.Name, itemsFitting); } if (item.Quantity == 0) { itemsReady++; } } } } return(roundSummary); }
public void TestInitialize() { grill = new GrillViewModel(20, 30); //Mock Grill Menus menu1 = new GrillMenuModel( new System.Guid("99a08d4b-8e20-4811-beee-1b56ac545f90"), "Menu 04", new List <GrillMenuItemModel>() { new GrillMenuItemModel(new System.Guid("90ed4d57-7921-4c66-b208-4e312a9852e6"), "Paprika Sausage", 6, 3, "00:08:00", 40), new GrillMenuItemModel(new System.Guid("47614f4d-2621-40de-8be7-e35abed8ed44"), "Veal", 8, 4, "00:08:00", 10), }); menu2 = new GrillMenuModel( new System.Guid("3d88e518-0779-47b5-b395-492ce2a090ee"), "Menu 13", new List <GrillMenuItemModel>() { new GrillMenuItemModel(new System.Guid("2513c0e6-a8ec-412c-b8b7-b9b8695f3290"), "Item 3", 5, 3, "00:08:00", 20), new GrillMenuItemModel(new System.Guid("1f399e24-7c20-4f18-afb5-3a748cc79ce0"), "Item 4", 12, 5, "00:08:00", 10), }); menuList = new List <GrillMenuModel>(); }
//[TestCategory("TestDevelopment")] public void ThrowsExceptionWhenMenuItemIsOversized() { var config = GrillConfiguration.Default; var menu = new GrillMenuModel() { Items = new List <GrillMenuItemModel>() { new GrillMenuItemModel() { Id = Guid.NewGuid(), Width = config.GrillSize.Width + 1, Length = config.GrillSize.Height + 1, Name = "Oversized Menu 1", Quantity = 1 } } }; var planner = new DefaultGrillMenuPlanner(config); GrillMenuGrillingPlan plan = planner.Plan(menu); }
/// <summary>Plans the given menu.</summary> /// <param name="menu">The menu to be planned for grilling.</param> /// <returns>The plan for the grilling.</returns> /// <remarks>This method plans the grilling of the menu.</remarks> public override GrillMenuGrillingPlan Plan(GrillMenuModel menu) { var plan = new GrillMenuGrillingPlan(); var grill = new Grill(GrillConfiguration); // Convert given GrillMenuModel instance into Dictionary<GrillItem, int> Dictionary <GrillItem, int> newMenu = ValidateAndCreateMenu(menu); while (true) { var newMenuItems = (from newMenuItem in newMenu.Keys where newMenu[newMenuItem] != 0 select newMenuItem).ToArray(); // Loop will continue if there are items to be added; otherwise, it will break if (!newMenuItems.Any()) { break; } TimeSpan maxTimeSpan = new TimeSpan(0, 0, 0); // Iterate on items with quantity > 0 and add them to to grill foreach (var grillItem in newMenuItems) { int addedCount = grill.AddMenuItem(grillItem, newMenu[grillItem]); // We may not be able to place every item since grill size is limited. newMenu[grillItem] -= addedCount; if (grillItem.CookingTime > maxTimeSpan) { maxTimeSpan = grillItem.CookingTime; } } // Apply the results to the plan. plan.Rounds++; plan.ElapsedTime += (uint)maxTimeSpan.TotalSeconds; // Clear the grill for the new round. grill.Clear(); } return(plan); }
private Dictionary <GrillItem, int> ValidateAndCreateMenu(GrillMenuModel menu) { var newMenu = new Dictionary <GrillItem, int>(); foreach (var grillMenuItem in menu.Items ?? new List <GrillMenuItemModel>()) { int quantity = grillMenuItem.Quantity.GetValueOrDefault(0); if (quantity <= 0) { continue; } int width = grillMenuItem.Width.GetValueOrDefault(0); if (width <= 0) { throw new BusinessException("The Width of the GrillMenuItemModel with the id {0} is not set.", grillMenuItem.Id.Value); } int length = grillMenuItem.Length.GetValueOrDefault(0);; if (length <= 0) { throw new BusinessException("The Length of the GrillMenuItemModel with the id {0} is not set.", grillMenuItem.Id.Value); } if (width > GrillConfiguration.GrillSize.Width || length > GrillConfiguration.GrillSize.Height) { throw new BusinessException("The Size of the GrillMenuItemModel exceeds the Grill.", grillMenuItem.Id.Value); } TimeSpan duration; TimeSpan.TryParseExact(grillMenuItem.Duration, "hh\\:mm\\:ss", CultureInfo.InvariantCulture, out duration); var size = new Size(width, length); newMenu.Add(new GrillItem(size, duration), quantity); } return(newMenu); }
/// <summary>Plans the given menu asynchronously.</summary> /// <param name="menu">The menu to be planned for grilling.</param> /// <returns>The task that represents the plan for the grilling.</returns> public virtual async Task <GrillMenuGrillingPlan> PlanAsync(GrillMenuModel menu) { return(Plan(menu)); }
/// <summary>Plans the given menu.</summary> /// <param name="menu">The menu to be planned for grilling.</param> /// <returns>The plan for the grilling.</returns> /// <remarks>This method is being used by other methods and left as abstract. In order to have the advantage of this base class, just override this method.</remarks> public abstract GrillMenuGrillingPlan Plan(GrillMenuModel menu);