AlgoMaster Logo
AlgoMasterDesign Menu Systemeasy

Design Menu System

easy

Picture a restaurant menu with sections such as Drinks, Hot Drinks, and Coffee. A section can contain individual dishes, but it can also contain smaller sections. No matter how deeply the menu is nested, the restaurant still needs to render it, count its items, total its prices, and report its depth.

This is a natural fit for the Composite pattern: an item and a submenu should be usable through the same component contract. The starter code already includes RestaurantMenu, including id management and node insertion. Your job is to implement only these three pattern participants:

  • MenuComponent, the shared contract used by both kinds of menu node.
  • MenuLeaf, which represents one priced item.
  • MenuGroup, which stores child components and combines their results recursively.

The provided RestaurantMenu facade behaves as follows:

  • RestaurantMenu(String rootName) creates a menu whose root is an empty submenu with that name. The root always has id 0.
  • int addItem(int parentId, String name, double price) adds an item under the submenu with that id and returns the new node's id. It returns -1 when no node has that id, or when that node is an item rather than a submenu.
  • int addSubMenu(int parentId, String name) adds an empty submenu the same way and returns its id, or -1 under the same two conditions.
  • String render() returns the whole menu as text.
  • int itemCount() returns how many items sit anywhere below the root.
  • String total() returns the sum of every item price below the root, to two decimal places.
  • int depth() returns how many levels the menu has. A root on its own is 1.

Ids are handed out in order starting at 1, and an add that returns -1 consumes no id.

render writes a submenu as its name followed by a colon, and an item as its name, a hyphen, and its price with a dollar sign and two decimal places. Every node is indented two spaces further than its parent, and the text carries no trailing newline.

The tests call RestaurantMenu, which in turn delegates the real tree work to your component classes. Do not reimplement the facade.

Example 1:

Input:

Output:

Explanation: Two items sit directly under the root and two more inside Drinks, so itemCount reaches 4 rather than 3. The two drink lines are indented four spaces because the walk went two levels down to reach them.

Example 2:

Input:

Output:

Explanation: Espresso sits three levels below the root, which puts its line six spaces in and makes depth 4. Its price counts toward the total exactly like Bagel, which sits directly under the root.

Constraints

  • 0 <= parentId <= 200
  • 0.00 <= price <= 1000.00, with at most two decimal places
  • Names contain letters, digits and spaces only.
  • At most 100 calls in total are made across all methods.

Starter Code

Only the three Composite participants are unfinished. Implement the shared component contract, the item leaf, and the submenu composite at the marked locations. RestaurantMenu is already implemented and should not be rewritten.

How the design is graded

needs 7/10 to pass
  • One contract for both kinds of node

    Full marks when an item and a submenu implement the same component interface, a submenu holds one list of that interface, and no aggregate or render method asks which concrete child type it received. Lose points heavily when the submenu keeps items and submenus in separate lists or stores children as concrete leaf types.

  • Aggregation recurses to the bottom

    Full marks when a submenu produces `itemCount`, the price total, `depth` and `render` by calling the same method on each child and combining what comes back, so a menu four levels deep reports correctly. Lose points heavily when a submenu counts its direct children, when rendering stops after one level, or when the price total skips nested submenus.

  • Leaf and group behavior

    Full marks when an item reports a count of 1, its own price and depth 1, while an empty submenu reports count 0, total 0 and depth 1. Rendering must add two spaces per level, format item prices to two decimal places, and return strings instead of printing to stdout.

Passing every test is not enough on its own. A submission is accepted only when the design also clears the bar.

Hints

Loading...
CallReturns
new RestaurantMenu("Main Menu")null
addItem(0, "Burger", 8.99)1
addItem(0, "Fries", 3.99)2
addSubMenu(0, "Drinks")3
addItem(3, "Cola", 1.99)4
addItem(3, "Water", 0.99)5
render()"Main Menu:\n Burger - $8.99\n Fries - $3.99\n Drinks:\n Cola - $1.99\n Water - $0.99"
itemCount()4
total()"15.96"

Two items sit directly under the root and two more inside `Drinks`, so `itemCount` reaches 4 rather than 3. The two drink lines are indented four spaces because the walk went two levels down to reach them.

Run checks these cases. Submit also runs a larger hidden set.