Columnas calculadas/calculadas en PostgreSQL
postgresql materialized view performance (5)
¡Una forma de hacer esto es con un gatillo!
CREATE TABLE computed(
one SERIAL,
two INT NOT NULL
);
CREATE OR REPLACE FUNCTION computed_two_trg()
RETURNS trigger
LANGUAGE plpgsql
SECURITY DEFINER
AS $BODY$
BEGIN
NEW.two = NEW.one * 2;
RETURN NEW;
END
$BODY$;
CREATE TRIGGER computed_500
BEFORE INSERT OR UPDATE
ON computed
FOR EACH ROW
EXECUTE PROCEDURE computed_two_trg();
El disparador se dispara antes de que se actualice o inserte la fila. Cambia el campo que queremos calcular de NEW
registro y luego devuelve ese registro.
¿PostgreSQL admite columnas calculadas / calculadas, como MS SQL Server? No puedo encontrar nada en los documentos, pero como esta característica está incluida en muchos otros DBMS, pensé que podría estar perdiendo algo.
Por ejemplo: http://msdn.microsoft.com/en-us/library/ms191250.aspx
PostgreSQL no admite "Columnas calculadas" per se hasta al menos Postgres 11.
Vea el comentario de f90t sobre la función en desarrollo, pero todavía no parece que vaya a ser en Postgres 11 .
Puede implementar una funcionalidad similar con una view .
O puede usar funciones que funcionan y se parecen a columnas calculadas .
Explicación detallada en esta respuesta relacionada:
Las columnas calculadas "persistentes" se pueden implementar con triggers de una manera funcionalmente idéntica.
Las vistas materializadas son un concepto estrechamente relacionado, implementado desde Postgres 9.3 .
En versiones anteriores, uno puede administrar MVs de forma manual.
Tengo un código que funciona y uso el término calculado, no estoy en postgresSQL puro aunque ejecutemos en PADB
aquí es cómo se usa
create table some_table as
select category,
txn_type,
indiv_id,
accum_trip_flag,
max(first_true_origin) as true_origin,
max(first_true_dest ) as true_destination,
max(id) as id,
count(id) as tkts_cnt,
(case when calculated tkts_cnt=1 then 1 else 0 end) as one_way
from some_rando_table
group by 1,2,3,4 ;
Una solución liviana con restricción Check:
CREATE TABLE example (
discriminator INTEGER DEFAULT 0 NOT NULL CHECK (discriminator = 0)
);
¡¡Sí tu puedes!! La solución debe ser fácil, segura y eficiente ...
Soy nuevo en postgresql, pero parece que puede crear columnas calculadas mediante el uso de un índice de expresión , emparejado con una view (la vista es opcional, pero hace la vida un poco más fácil).
Supongamos que mi cálculo es md5(some_string_field)
, luego creo el índice como:
CREATE INDEX some_string_field_md5_index ON some_table(MD5(some_string_field));
Ahora, cualquier consulta que actúe en MD5(some_string_field)
utilizará el índice en lugar de calcularlo desde cero. Por ejemplo:
SELECT MAX(some_field) FROM some_table GROUP BY MD5(some_string_field);
Puedes verificar esto con explain .
Sin embargo, en este momento confía en los usuarios de la tabla que saben exactamente cómo construir la columna. Para hacer la vida más fácil, puede crear una VIEW
en una versión aumentada de la tabla original, agregando el valor calculado como una nueva columna:
CREATE VIEW some_table_augmented AS
SELECT *, MD5(some_string_field) as some_string_field_md5 from some_table;
Ahora cualquier consulta que use some_table_augmented
podrá usar some_string_field_md5
sin preocuparse por cómo funciona ... solo obtienen un buen rendimiento. La vista no copia ningún dato de la tabla original, por lo que es bueno para la memoria y para el rendimiento. Sin embargo, tenga en cuenta que no puede actualizar / insertar en una vista, solo en la tabla de origen, pero si realmente lo desea, creo que puede redirigir inserciones y actualizaciones a la tabla de origen usando rules (podría estar equivocado en ese último punto como Nunca lo intenté yo mismo).
Editar: parece que si la consulta implica índices competitivos, el motor del planificador a veces puede no usar el índice de expresión en absoluto. La elección parece depender de los datos.