Menu
Coddy logo textTech

Снимок инвентаря

Часть раздела Логика и управление потоком путешествия по Ruby на Coddy — урок 55 из 56.

Отчет об инвентаризации, который задействует хеши, цепочки Enumerable, group_by и немного форматирования.

challenge icon

Задание

Средне

Дан массив inventory. Каждый элемент представляет собой хэш с ключами :name, :category, :qty и :price.

Выведите четыре строки:

  1. Общая стоимость всех товаров в инвентаре (сумма qty * price), выведенная как целое число.
  2. Категория с наибольшим количеством наименований товаров в формате Top category: <name> (<count>). При равном количестве выбирайте категорию, идущую первой по алфавиту.
  3. Названия товаров, которых нет в наличии (qty == 0), отсортированные по алфавиту и разделенные запятой с пробелом , . Если таких товаров нет, выведите (none).
  4. Названия 3 самых дорогих товаров по цене за единицу, от самых дорогих к менее дорогим, разделенные , . При равной цене сортируйте по названию в алфавитном порядке.

Для инвентаря по умолчанию вывод будет следующим:

232
Top category: food (3)
milk
chair, lamp, milk

Шпаргалка

Работа с массивами хешей с использованием методов Enumerable:

# Сумма с вычислением для каждого элемента
inventory.sum { |item| item[:qty] * item[:price] }

# Группировка по ключу и подсчет
groups = inventory.group_by { |item| item[:category] }
groups.max_by { |cat, items| [items.count, ...] }

# Фильтрация, сортировка и объединение
inventory.select { |item| item[:qty] == 0 }
         .map { |item| item[:name] }
         .sort
         .join(", ")

# Сортировка по нескольким критериям (при совпадении — по алфавиту)
inventory.sort_by { |item| [-item[:price], item[:name]] }
         .first(3)
         .map { |item| item[:name] }
         .join(", ")

Разрешение конфликтов по алфавиту при использовании max_by с подсчетом:

# Побеждает большее количество; при равенстве — первый по алфавиту (отрицание строки для max_by)
groups.max_by { |cat, items| [items.count, -cat.ord] }
# Или используйте min_by с отрицательным количеством + естественный порядок строк
groups.sort_by { |cat, items| [-items.count, cat] }.first

Попробуйте сами

inventory = [
  { name: "apple",  category: "food",        qty: 10, price: 2 },
  { name: "bread",  category: "food",        qty: 4,  price: 3 },
  { name: "milk",   category: "food",        qty: 0,  price: 4 },
  { name: "chair",  category: "furniture",   qty: 2,  price: 35 },
  { name: "lamp",   category: "furniture",   qty: 5,  price: 20 },
  { name: "pencil", category: "stationery",  qty: 30, price: 1 }
]

# TODO: вывести общую стоимость, самую популярную категорию, названия товаров не в наличии, топ-3 по цене
quiz iconПроверьте себя

В этом уроке есть небольшой тест. Начните урок, чтобы ответить на вопросы и сохранить прогресс.

Все уроки раздела Логика и управление потоком