Делаю уже пол года скоро систему учета здоровья для универской кафедры, времени мало, дело медленно идет, но идет. В декабре закончил с формами заполнения, сейчас перешел к построению отчетов и возникла интересная задача, которая решилась прямо по учебнику, сам удивился. Так понравилось это, что решил написать про нее на память.
Смысл такой. Есть много студенческих групп, в каждой есть представители мужского и женского пола, все они оцениваются единой методикой оценки здоровья по нескольким измеряемым параметрам (это входные данные). Есть 6 уровней градации здоровья каждого студента: низкий, ниже среднего, средний, выше среднего, высокий. Программа автоматически определяет этот тип по входным данным и затем сохраняет в базе данных. Задача состоит в том, чтобы можно было для произвольной группы (или нескольких групп) заказывать отчет о том, сколько процентов студентов имеют тот или иной тип здоровья, причем нужно разделать юношей и девушек, а также иметь возможность строить отчет по разным годам обучения (например 1 и 3, 3 и 4, 1,2,3,4 и т.д.)
Сначала задача мне показалась простой и я попробовал решить ее в лоб. В базе данных есть вся необходимая информация, слепил интерфейс для выбора параметров отчета, которые дают мне предложение WHERE для SQL-запроса, получил результат, стал разбирать. И вот тут начались трудности, потому что я стал путаться в обилии информации.
Нужно было как-то разделять данные, для каждой группы создавать два массива - один для юношей, другой для девушек, потом не забывать, что такие массивы нужны для каждого года, а с учетом того, что групп может быть и несколько, голова совсем пошла кругом.
Я приуныл, все-таки попробовал разобрать эту свалку, но не вышло, куча ошибок, код ужасный выходил, бросил это дело, стал думать. Вспомнил слова Вирта о том, что программа это алгоритмы + структуры данных. И вот тут меня осенило и все пошло как по маслу дальше. Надо было просто применить классическую декомпозицию сложной задачи. Я порисовал схемы в тетрадке и в итоге получилось дерево. В корне стоит объект, который собирает информацию от групп, от групп идут ветви к годам обучения, от каждого года идет две ветки к результатам для каждого пола, от пола уже идет множество веток - результаты тестов каждого студента.
Теперь для получения информации нужно просто задать корню вопрос - получить информацию по такой-то группе, за такой-то год обучения, для такого-то пола студентов. Корень выбирает нужную группу и передает ей остальные параметры, группа выбирает год обучения, передает оставшееся ему, год обучения выбирает пол студента и последний возвращает все присоединенные к нему результаты.
Таким образом остается только задать корню все вопросы, сохранить результаты в массивах и вывести на экран. Редко получается так осмысленно применить декомпозицию и получить ощутимый результат от ее использования. Здорово.