Модернизирую мат. модель летательного аппарата. Вопрос по стилистике. Как красивее, четче и понятнее переложить численные решения кучи диф.ур на С++?
Опыт предписывает сделать класс, инкапсулирующий все данные, используемые моделью. Public-свойства (через методы чтения/записи) дадут потребителю доступ к входным и выходным параметрам модели, а метод-обработчик Handler() позволит считать модель в обработчике таймера с нужным шагом.
Вопросы:
1) Очень много параметров. Стоит ли внутри класса объединять их в какие-то логические структуры/объединения и т.д.? Структура станет четче, но код вырастет в разы, а он и так не маленький.
2) Как красивее оформить саму математику?
Хотелось бы, чтобы каждый метод класса реализовывал свою функцию, которая преобразовывает входной вектор параметров Х в выходной Y, который используется как входой для следующей функции и т.д до конца — четкая цепочка вычислений вход-выход. Но т.к. входов-выходов у каждой функции получается слишком много (а они еще и векторные), читабельность ухудшается. Насколько приемлемо стилистически делать методы без параметров, которые просто преобразовывают внутренние поля класса "втихаря"?
void CModel::Handler()
{
CalcAerodynamics();
CalcEngine();
CalcAngles();
...
...
...
}
3)Как лучше с точки зрения читабельности кода возвращать результат функции (метода), если ее выходом является сразу несколько параметров? Можно задать структуру и возвращать указатель на нее через return, можно на вход передать кучу ссылок на внешние переменные (поля класса), которые функция изменит. Можно задавать на вход кучу указателей на, по которым функция (метод) запишет выходные параметры. Можно вообще ничего не задавать, а молча изменять значения полей класса и все.
Уважаемые гуру, поделитесь опытом плиз!
Здравствуйте, ND322, Вы писали:
ND>Модернизирую мат. модель летательного аппарата. Вопрос по стилистике. Как красивее, четче и понятнее переложить численные решения кучи диф.ур на С++?
Прежде всего надо определиться: что является классом?
Вот, например (из приведенного краткого описания), явно видны три класса:
CAerodynamics
CEngine
CAngles
По всей вероятности, это разные понятия (т.е. базовый класс выделить не можем), но это только мое предположение. Я не специалист по данной тематике.
Каждый класс включает как параметры (члены класса, доступные через публичные методы), так и расчетные функции, реализующие алгоритмы расчета для летательных аппаратов.
Методы класса, которые принимают по 10-15 параметров, как правило воспринимаются с трудом, т.е. дальнейшая поддержка кода будет делом малоприятным. Намного правильнее передавать функции (методу) указатель на структуру, для чего наряду с "тяжеловесными" классами, необходимо предусмотреть простые структуры данных. Эти структуры будут представлять набор данных для методов класса. Впрочем, передача указателя (или ссылки) на класс также вполне допустима.
Нежелательно писать очень длинные методы класса — можно просто разбить на две-три отдельных метода и подобрать соответствующие названия. Сложно разобраться (особенно тому, кто увидит твой код), когда в одном методе будет более сотни строк кода.
Затем определиться с коллекциями (вектора, мап-ы, сет-ы) объектов для каждого из классов.
Здесь я полагаю (как мое предпочтение) применение STL коллекций. Хотя, конечно же, привязка к STL не обязательна.
Далее следует четко представить действия пользователя и выбрать наиболее удобный графический интерфейс приложения (GUI).
Также следует придерживаться какого-то стандарта при именовании классов/членов класса/методов/локальных переменных и структур.
А теперь — в путь
Здравствуйте, ND322, Вы писали:
ND>Модернизирую мат. модель летательного аппарата. Вопрос по стилистике. Как красивее, четче и понятнее переложить численные решения кучи диф.ур на С++?
ND>3)Как лучше с точки зрения читабельности кода возвращать результат функции (метода), если ее выходом является сразу несколько параметров? Можно задать структуру и возвращать указатель на нее через return, можно на вход передать кучу ссылок на внешние переменные (поля класса), которые функция изменит. Можно задавать на вход кучу указателей на, по которым функция (метод) запишет выходные параметры. Можно вообще ничего не задавать, а молча изменять значения полей класса и все.
ND>Уважаемые гуру, поделитесь опытом плиз!
Могу только по третьему пункту посоветовать, если параметров много, то объединить их в структуру (потом можно будет легко выделить в отдельный класс который рассчитывает только эти параметры), лучше указатель сверху спускать или ссылку, зачем делать грабли на пустом месте с владением указателя когда его удалять когда нет.
Либо
// true расчет удался, в result все расчитаные данные
bool Func(SResult* result)
{
...
}
Либо boost::tuple можно использовать
Если все параметры являются полями класса, то тогда зачем их передовать? Разделите данные и алгоритм расчета.