Firebird: вычисление пользовательских формул.

Модератор: Модераторы

Firebird: вычисление пользовательских формул.

Сообщение wofs » 30.03.2018 22:55:21

Доброго дня.
В приложении для пущей гибкости расчета цен было решено использовать формулы.
Хочется возможность использовать нечто вроде:
Код: Выделить всё
ROUND(IF(A>B,C,D),2)

//где A,B,C,D - может быть значениями полей в запросе, числами, датами, фазами луны или выражениями.


Пока решил с помощью fpexprpars и создания в датасете вычисляемого поля. Все устраивает, за исключением.... сортировки. Что и логично - данного поля то на сервере нет.
В таблице строк может быть достаточно много (over 100k) и тянуть их все на клиента, а потом локально сортировать дело неблагодарное.

Вот и возник вопрос: А как вычислять пользовательские формулы на стороне сервера?
Может кто-то решал данную задачу - поделитесь, если не решением, то советом. Может есть решения на базе других БД.

p.s. Хотел было написать UDFку, но обнаружилось, что из UDF нет возможности доступа к БД. То есть придется каждый раз передавать параметром в UDF формулу, парсить ее и считать - боюсь за скорость всего этого...
Аватара пользователя
wofs
постоялец
 
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань

Re: Firebird: вычисление пользовательских формул.

Сообщение alexs » 31.03.2018 00:56:42

Вариант с массовым просчётом цен технологической работой с клиента и сохранением их в БД не подходит? Например - пересчёт вечером для работы на следующий день.
Аватара пользователя
alexs
долгожитель
 
Сообщения: 4053
Зарегистрирован: 15.05.2005 23:17:07
Откуда: г.Ставрополь

Re: Firebird: вычисление пользовательских формул.

Сообщение olegy123 » 31.03.2018 07:44:37

wofs писал(а):Вот и возник вопрос: А как вычислять пользовательские формулы на стороне сервера?
можно же использовать CREATE FUNCTION/CREATE PROCEDURE
на выходе иметь нужную, отсортированную таблицу.

wofs писал(а):UDFку
оно нужно для расширения базового языка..
olegy123
долгожитель
 
Сообщения: 1643
Зарегистрирован: 25.02.2016 12:10:20

Re: Firebird: вычисление пользовательских формул.

Сообщение wofs » 31.03.2018 10:36:31

alexs писал(а):Вариант с массовым просчётом цен технологической работой с клиента и сохранением их в БД не подходит? Например - пересчёт вечером для работы на следующий день.

Нечто подобное, возможно, будет в следующем проекте, там это уместнее.

Задача этой утилиты работа с прайс-листами и создания на основе их некоего каталога с несколькими колонками. В принципе, можно рассчитывать цены при загрузке прайс-листов, но здесь тоже проблема - количество колонок неограничено, поэтому под цены отдельную таблицу и получим кучу джойнов при выборке на каждую позицию, да еще и с фильтрацией по ценовой колонке.

Прежде хотелось бы узнать - вдруг есть решения все это делать на стороне сервера.

olegy123 писал(а):можно же использовать CREATE FUNCTION/CREATE PROCEDURE
на выходе иметь нужную, отсортированную таблицу.

А вот здесь я совсем не понял, поясните, пожалуйста.
Аватара пользователя
wofs
постоялец
 
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань

Re: Firebird: вычисление пользовательских формул.

Сообщение olegy123 » 31.03.2018 11:19:00

http://www.realcoding.net/article/view/1576

Добавлено спустя 4 минуты 9 секунд:
попроще
https://www.ibase.ru/sp_call/
olegy123
долгожитель
 
Сообщения: 1643
Зарегистрирован: 25.02.2016 12:10:20

Re: Firebird: вычисление пользовательских формул.

Сообщение wofs » 31.03.2018 11:52:07

olegy123 писал(а):попроще

Про ХП я знаю, я не совсем понимаю как это применительно к моей ситуации.

Пользователь самостоятельно создает ценовые колонки (неограниченное количество) и каждой колонке назначает формулу для расчета, используя доступные функции и переменные.
В данный момент расчет происходит в локальном датасет. То есть на сервере результата расчета нет. Следовательно сортировать там нечего.

Признаюсь, в плане ХП была задумка "парсить формулу" на сервере и в ХП расчитывать результат, делая выборку на клиента через for select, но я не представляю с какого конца подступиться и как все это скажется на производительности.
Аватара пользователя
wofs
постоялец
 
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань

Re: Firebird: вычисление пользовательских формул.

Сообщение vitaly_l » 31.03.2018 11:55:35

wofs писал(а):Пользователь самостоятельно создает ценовые колонки (неограниченное количество) и каждой колонке назначает формулу для расчета, используя доступные функции и переменные.

Ну и внесите эти формулы на сервер и там считайте. В чём проблема?
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Firebird: вычисление пользовательских формул.

Сообщение wofs » 31.03.2018 12:05:01

vitaly_l писал(а):Ну и внесите эти формулы на сервер и там считайте. В чём проблема?

Я правильно понял - вы предлагаете формулы просто вставлять в запрос при его формировании на клиенте и пусть сервер их считает?
А сами формулы писать с учетом синтаксиса SQL или создавать необходимые функции посредством ХП?

Пока писал появилась такая мысль.
1. Пишем формулу на клиенте и сохраняем в таблицу на сервере (эта часть есть).
2. При выборе нужной ценовой колонки просто заменяем переменные формулы на имена соответствующего поля в выборке и подставляем результат в SQL запрос перед отправкой онного на сервер.
3. Сервер рассчитывает формулу в запросе и получаем нормальное поле на стороне сервера с необходимыми данными.

Это будет работать?
Аватара пользователя
wofs
постоялец
 
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань

Re: Firebird: вычисление пользовательских формул.

Сообщение vitaly_l » 31.03.2018 12:12:04

wofs писал(а):сами формулы писать с учетом синтаксиса SQL

Да.
wofs писал(а): просто заменяем переменные формулы на имена соответствующего поля в выборке и подставляем результат в SQL запрос перед отправкой онного на сервер.

Да.
wofs писал(а):Это будет работать?

Да.
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Firebird: вычисление пользовательских формул.

Сообщение wofs » 31.03.2018 12:36:26

Спасибо всем!
Аватара пользователя
wofs
постоялец
 
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань

Re: Firebird: вычисление пользовательских формул.

Сообщение vitaly_l » 31.03.2018 12:41:12

wofs писал(а):Спасибо всем!

Код: Выделить всё
create procedure calcsalarysum
returns (fn varchar(15), ln varchar(20), sm numeric(15,2))
as
declare variable s numeric(15,2);
begin
  sm=0;
  for select first_name, last_name, salary
      from employee
      into :fn, ln, :s
  do
    begin
      sm=:sm+:s;
      suspend;
    end
  fn='';
  ln='';
  s=:sm;
  suspend;
end;

подробнее см. https://www.ibase.ru/sp_call/
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Firebird: вычисление пользовательских формул.

Сообщение olegy123 » 31.03.2018 13:15:25

wofs писал(а):Признаюсь, в плане ХП была задумка "парсить формулу" на сервере и в ХП расчитывать результат, делая выборку на клиента через for select, но я не представляю с какого конца подступиться и как все это скажется на производительности.

на сколько я знаю, в FB нет понятия таблица с изменяемыми колонками.. как и нет выполнение команды из VARCHAR() переменной и вывод некой вариативной таблицы. Отсюда JSON FB не умеет - поэтому в WEB-ке его не любят использовать. Точно не знаю что добавили в Firebird 3.0.
Зато есть TEMPORARY TABLE.

Работать с DataSet на стороне клиента.. записей не много, активности обновлений не высокая.. в конце концов есть же всякие TMemoryTable и т.п.
olegy123
долгожитель
 
Сообщения: 1643
Зарегистрирован: 25.02.2016 12:10:20

Re: Firebird: вычисление пользовательских формул.

Сообщение wofs » 31.03.2018 13:30:15

olegy123 писал(а):Работать с DataSet на стороне клиента.. записей не много, активности обновлений не высокая.. в конце концов есть же всякие TMemoryTable и т.п.

Очень не хотелось бы тащить все записи на клиента. И не только из-за объема. Прайс-листы (данные из которых так же являются основанием для расчета) могут обновиться в фоне (как и курс валют) и может получиться так, что на клиенте окажутся неактуальные данные, а это очень нехорошо.

Ведь, как выяснилось, далеко не всегда я буду сам ей пользоваться, а это обязывает к некоторой ответственности.
Аватара пользователя
wofs
постоялец
 
Сообщения: 379
Зарегистрирован: 05.10.2009 10:16:55
Откуда: Астрахань

Re: Firebird: вычисление пользовательских формул.

Сообщение alexs » 02.04.2018 10:13:59

olegy123 писал(а):на сколько я знаю, в FB нет понятия таблица с изменяемыми колонками.. как и нет выполнение команды из VARCHAR() переменной и вывод некой вариативной таблицы.

Такие вещи реализуются просто
В таблице хранишь структуру - Номер Столбца, Значение Столбца. Именно так я реализовал у себя прайслисты.
wofs писал(а):Очень не хотелось бы тащить все записи на клиента.
И
Как вариант - можно сделать простейший парсер-компилятор на стороне клиента. Его задача будет превращать конструкции из формата fpexprpars в формат функций firebird-а. И передовать в базу уже готовые выражения SQL для выполнения через execute.
Кстати - если использовать FB3 - то там уже есть полноценные функции.
Аватара пользователя
alexs
долгожитель
 
Сообщения: 4053
Зарегистрирован: 15.05.2005 23:17:07
Откуда: г.Ставрополь

Re: Firebird: вычисление пользовательских формул.

Сообщение olegy123 » 02.04.2018 13:24:13

alexs писал(а):Как вариант - можно сделать простейший парсер-компилятор на стороне клиента.

ага.. самое простое решение.
olegy123
долгожитель
 
Сообщения: 1643
Зарегистрирован: 25.02.2016 12:10:20

След.

Вернуться в Базы данных

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 3

Рейтинг@Mail.ru