Для начала нам нужно определиться: каким образом мы будем определять отношение введеной пользователем суммы к предлагаемым категориями.
Удобства ради, и потому что я не представляю как по другому, нам нужно представить категорию как целое число, чтобы в дальнейшем мы могли сравнить его с введеной суммой.
Так как у нас есть произвольное кол-во категорий с рядом затрат в кол-ве n, где каждая затрата это целое число, то каждую категорию можно представить как (мульти)множество мощностью n
Дальше есть несколько вариантов, как преобразить это множество в целое число:
- Взять среднее арифмитическое от этого множества
- Взять медиану от этого множества
Я склоняюсь ко второму варианту, так как множества трат у большинства категорий имеют ненормальное распределение, например, продукты или проезд: взятие среднего арифмитического не будет показывать "среднего", типичного размера траты, потому как проезд может быть на общественном транспорте и на такси, на первом люди ездят чаще или также покупка бутылки воды в магазине отличается от поездки за продуктами "на неделю".
Далее, нам нужно отсортировать категории по подходимости: от большей к меньшей. Подходимость(честно, я не знаю есть ли такое слово) можно выразить в:
- модуле разности "среднего" размера траты категории и введенной суммы
- кол-ва трат в данной категории, можно сказать частотность
Иными словами у нас есть два поля сортировки. Первичная, разница трат, и вторичная, частотность.
Подытожим, какой получается алгоритм:
- Берем имеющийся на данный момент список затрат, на его основе получаем список, состоящий из названия категории, "средней" суммы в данной категории и кол-во затрат(записей затрат) в данной категории.
- Отображаем получившийся список, используя введеную пользователем сумму и приводим к виду: название категории, разница сумм, частотность
- Сортируем: по разнице от меньшей к большему и по частотности от большей к меньшему.
И получаем список который можно отдавать пользователю.
PS: Для меня осталось загадкой как конкретно использовать даты в данном случае. Я предполагаю, что можно проанализировать, что какие то траты пользователь делает только в опредленные промежутки месяца или года. Но я не стал накручивать. Если был неправ, думаю вы мне скажете :)
Выполнить в следующей последовательности:
- create.sql создаст таблицы в вашей базу
- functions.sql декларирует нужные функции
- seed.sql заполнит базу dummy data
Все файлы в корне репы
Для проверки выполнить
SELECT * FROM get_suitable_categories(num);
где num
это сумма введенная пользователем