Создание представления частот из таблицы с неизвестным количеством столбцов - PullRequest
0 голосов
/ 22 ноября 2011

У меня есть таблица с n столбцами, и мне нужно создать представление, которое содержит частоты каждого уникального значения в каждом столбце.n неизвестно, так как мне нужно применить решение к многочисленным таблицам с различным количеством столбцов.

Например, у меня есть таблица:

column1  column2  column3
value1   value2   value3
value2   value2   value1
value1   value2   value2

Представление должно быть примерно таким:

columnname    value    frequency

 column1      value1    2
 column1      value2    1
 column2      value2    3

...

Поскольку у меня очень мало опыта работы с sql, любая помощь будет чрезвычайно признательна.

Заранее большое спасибо!

Таким образомЯ до сих пор придумывал это, но сейчас вроде как обескуражен.

CREATE or REPLACE FUNCTION create_view () RETURNS setof record AS $$
DECLARE   
col RECORD;
BEGIN
for col in execute 'select column_name from information_schema.columns 
where table_name = ''table123''' LOOP
    ???
END LOOP;
return;
END;
$$
LANGUAGE 'plpgsql';

1 Ответ

0 голосов
/ 22 ноября 2011

Простой SQL:

SELECT 'col1' AS col, col1 AS val, count(*) AS ct FROM  tbl GROUP BY col1
UNION ALL
SELECT 'col2', col2, count(*) FROM  tbl GROUP BY col2
UNION ALL
SELECT 'col3', col3, count(*) FROM  tbl GROUP BY col3

Функция PL / pqSQL, выполняющая динамический SQL:

CREATE OR REPLACE FUNCTION f_demo(_schema text, _tbl text)
  RETURNS TABLE(col text, val text, ct bigint) AS
$xx$
DECLARE   
   _fld text;
   _sql text := '';
BEGIN

FOR _fld IN  
   SELECT a.attname          -- use quote_ident to safeguard against SQLi
   FROM   pg_catalog.pg_attribute a
   WHERE  a.attrelid =  (COALESCE(_schema || '.', '') || _tbl)::regclass
   AND    a.attnum > 0
   AND    NOT a.attisdropped
-- AND    a.attname ~~ '%col%'   -- if you want to pick specific columns
LOOP
   RETURN QUERY EXECUTE
  'SELECT $1, ' || quote_ident(_fld) || '::text, count(*)
   FROM ' || COALESCE(quote_ident(_schema) || '.', '') || quote_ident(_tbl) || '
   GROUP BY 2'
   USING _fld;
END LOOP;

END;
$xx$
  LANGUAGE 'plpgsql';

Вызов:

SELECT * FROM f_demo('public', 'mytable');

Или, если вы хотите использоватьсхема, указанная в search_path:

SELECT * FROM f_demo(NULL, 'mytable');

Основные точки

  • Работает для для любой таблицы и для любого количества столбцов с значения любого типа .
  • Значения приводятся к тексту, чтобы упростить мой пример.Может быть сделано и с полиморфным типом.
  • См. Этот связанный ответ для получения информации о методах и ссылках plpgsql: https://stackoverflow.com/q/8146245/939860
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...