Андрейка
"Начинаем с построения модели" и до конца ее описания
Построение модели не зависит от использования/неиспользования ORM.
Рисую UML с сущностями и связями.
fisher
-> Конструктивная часть
Краткое описание псевдокода:
ORMFilter* - условия отбора.
ORMFilterEquality - условие "поле
равно значению"
ORMFilterLessEqual - условие "поле
меньше или равно значению"
ORMFilterCompositeAND - составное условие, для истинности которого необходима истинность всех частей
ORMFilterBoundObject - составное условие вида "
существует связанный объект типа X, для которого выполняется условие F(X)"(*)
ORMOrderCollection - набор правил сортировки
ORMOrderBoundAggregateCount - правило сортировки "по количеству связанных объектов типа X"
ORMFilterComposite::add_filter - добавить условие в составное условие
ORMManager::itemsFiltered - найти все существующие объекты заданного типа X (тип неявно задается конкретным экземпляром ORMManager), удовлетворяющие заданным условиям
Как возник код:
0. сформировано описание модели
1. Берем исходный запрос на человеческом языке
найти все компании, которые возят народ с ночевкой в барселоне (у кого-то там отель и он хочет продавать места в отеле оптом именно этим компаниям)
и выделяем в нем условия отбора(**):
(Найти компании, у которых есть остановка на маршруте (Waypoint)), (на которой есть ужин и которая находится в городе), (который имеет имя Барселона)
2. Видим три группы условий (выделены скобками), применяемых к сущностям Company, Waypoint и City.
Записываем их:
PHP:
// город имеет имя Барселона
$city_filter = ORMFilterEquality('title', 'Барселона');
// (на точке [i]есть[/i] ужин) И (точка [i]находится в[/i] городе)
$waypoint_filter = ORMFilterCompositeAND();
$waypoint_filter->add_filter(new ORMFilterBoundObject("Supper", new ORMFilterTrue()));
$waypoint_filter->add_filter(new ORMFilterBoundObject("City", $city_filter));
// у компании [i]есть[/i] остановка на маршруте (Waypoint)
$company_filter = ORMFilterBoundObject("Waypoint", $waypoint_filter);
Всё.
(*) как я уже говорил ранее, это не будет работать с кратными связями между сущностями. Легко обходится.
(**) на этапе работы с естественным языком большую роль играет человеческий фактор; тот же запрос можно разобрать как
Найти компании, у которых есть ужин, который проводится в городе, который имеет имя Барселона
и получить более компактный псевдокод.
PHP:
$city_filter = new ORMFilterEquality('title', "Florenzia");
$company_filter = new ORMFilterBoundObject("Supper",
new ORMFilterBoundObject('City', $city_filter));
$manager = ORMMetaclass::_get_manager("Company");
var_dump($manager->itemsFiltered(0, null, $company_filter));
...
-> Флейм
По поводу высказываний Sad Spirit, процитирую себя:
не надо, пожалуйста, сравнивать ООП и реляционную алгебру. Они соотносятся примерно так же, как функциональное программирование и Windows API.
Я надеюсь, что неглупые люди, способные абстрактно мыслить - со второго повторения - поймут,
что
объекты и взаимосвязи между ними легко описываются реляционной алгеброй,
что все НИР по теме "реляционная алгебра", таким образом, относятся и к ООП,
что SQL и есть "магическое связывание" и задание "таких и сяких фильтров" (см синтаксис FROM/WHERE/HAVING subclauses),
что "магическое связывание" в "псевдокоде" отсутствует, так как информация о связях содержится в описании модели и может быть использована ORM при формировании SQL-запроса,
что в ООП
есть отношения между объектами,
что думать в терминах отношений между сущностями ООП не запрещает,
что ORM позиционируется (мной) как способ скрыть детали реализации (в частности, скрыть существование промежуточных таблиц, через которые производится связывание),
что такое использование ORM позволяет работать с транзитивным отношением "связан с", а не искать каждый раз путь между связанными объектами
и что болезненное отношение Sad Spirit к словам "паттерны" и "рефакторинг" будет более-менее обосновано в том случае, если он сможет указать
алгоритмы, а не
эвристики построения модели (а не приведения существующей модели к нормальной форме).
Задачу сравнить размер и читаемость SQL запроса, выполняющего задачу (2), с размером и читаемостью псевдокода оставляем на отдельный разбор.