2016-10-26 4 views
1

Я использую Postgres для локального тестирования размещенной базы данных. В размещенной базе данных есть несколько функций, которых нет в Postgres. Мне не нужно реплицировать эти функции, но мне нужно иметь возможность вызывать функции с тем же именем и получать разумный ответ. Например, я хотел бы использовать функцию count для approximate_count_distinct. Пример запроса:Создайте псевдоним для встроенной агрегатной функции

 select approximate_count_distinct(id) 
    from table; 

Поведение этого запроса будет точно таким же, как и счет. Мне не нужно беспокоиться о том, что это не совсем то же самое, что и на размещенном db

Я просмотрел CREATE AGGREGATE, но не могу получить правильные аргументы. Вот то, что я пытался сделать для СОЗДАТЬ AGGREGATE:

CREATE AGGREGATE approximate_count_distinct(*) 
    ( 
    sfunc = count, 
    stype = bigint, 
    initcond = 0 
    ); 

но не компиляции, потому что он говорит ERROR: function count(bigint) does not exist

Я пытался найти правильный путь, чтобы объявить эту функцию, но получил безнадежно потерян. Я смотрел в pg_proc, но граф, казалось, был определен странным образом как aggregate_dummy как символическая ссылка src.

Я просмотрел ALIAS FOR, но это, похоже, не работает.

Короче говоря, я не знаю, что делать, чтобы заставить его работать. Конечно, должен быть простой способ сделать это?

+0

В чем проблема? выполнение функции или функция возвращает правильный результат? –

+0

Создание функции .. вот что я пытался сделать для CREATE AGGREGATE, но он не компилировался, потому что он говорит: «ERROR: function count (bigint) не существует» вот код 'CREATE AGGREGATE approximate_count_distinct (*) ( sfunc = count, stype = bigint, initcond = 0 ); '. постскриптум я попытался найти правильный способ объявить эту функцию, но безнадежно потерялся. Я смотрел в pg_proc, но граф, казалось, был определен странным образом как aggregate_dummy как символическая ссылка src. Короче говоря, я не знаю, что делать, чтобы заставить его работать – anv

+0

Опубликовать, что как часть вашего вопроса, в хорошем формате каждый может понять;) –

ответ

1

Используйте декларацию count(*) агрегата, просто измените имя:

create aggregate approximate_count_distinct(*) (
    sfunc = int8inc, 
    stype = int8, 
    initcond = '0' 
); 

select count(*), approximate_count_distinct(*) 
from generate_series(1, 100) 

count | approximate_count_distinct 
-------+---------------------------- 
    100 |      100 
(1 row) 

Вы можете использовать псевдотип anyelement как общий тип аргумента:

create aggregate approximate_count_distinct(anyelement) (
    sfunc = int8inc_any, 
    stype = int8, 
    initcond = '0' 
); 

select 
    approximate_count_distinct(id::int) as int, 
    approximate_count_distinct(id::dec) as dec, 
    approximate_count_distinct(id::text) as text 
from generate_series(1, 100) id 

int | dec | text 
-----+-----+------ 
100 | 100 | 100 
(1 row) 
+0

большое спасибо! Я думаю, что я понял, как сделать это для более общего типа данных 'создать совокупный approximate_count_distinct (VARCHAR) ( sfunc = int8inc_any, тампон = int8, initcond = '0' );' – anv

+0

См модифицированного ответа. – klin