如何在 PostgreSQL 中保留自动生成的列,即使删除了源列?

huangapple go评论105阅读模式
英文:

How do I keep auto-generated columns in PostgreSQL even after removing the source columns?

问题

我有一个包含自动生成列的表:

  1. -- 创建GEOGRAPHY点的函数,使用给定的输入
  2. create or replace
  3. function create_point_geography (long DOUBLE PRECISION, lat DOUBLE PRECISION)
  4. returns GEOGRAPHY
  5. language sql
  6. immutable
  7. as $$
  8. select ST_GeogFromText(CONCAT('SRID=4326;POINT(', long::text, ' ', lat::text, ')'))
  9. $$;
  10. CREATE TABLE driver_orders (
  11. id SERIAL PRIMARY KEY,
  12. driver_id INTEGER NOT NULL,
  13. address_from VARCHAR NOT NULL,
  14. address_to VARCHAR NOT NULL,
  15. active BOOLEAN DEFAULT true,
  16. date DATE NOT NULL,
  17. longitude_from DOUBLE PRECISION NOT NULL, -- 想要省略
  18. latitude_from DOUBLE PRECISION NOT NULL, -- 想要省略
  19. longitude_to DOUBLE PRECISION NOT NULL, -- 想要省略
  20. latitude_to DOUBLE PRECISION NOT NULL, -- 想要省略
  21. -- 添加自动生成的 'location_from'
  22. location_from GEOGRAPHY
  23. GENERATED ALWAYS AS
  24. (create_point_geography(longitude_from, latitude_from))
  25. stored,
  26. -- 添加自动生成的 'location_to'
  27. location_to GEOGRAPHY
  28. GENERATED ALWAYS AS
  29. (create_point_geography(longitude_to, latitude_to))
  30. stored
  31. );

正如您所看到的,有2列是基于其他列的值自动生成的。我想要删除名为 longitude_from, latitude_from, longitude_to, latitude_to 的列,这些列的值用于生成函数。但我想保留自动生成的列。所以,基本上我想要列 location_from, location_to 使用给定的值自动生成,而不是基于其他列。

这是否可能?

英文:

I have a table that has autogenerated columns:

  1. -- function that creates GEOGRAPHY point from given inputs
  2. create or replace
  3. function create_point_geography (long DOUBLE PRECISION, lat DOUBLE PRECISION)
  4. returns GEOGRAPHY
  5. language sql
  6. immutable
  7. as $$
  8. select ST_GeogFromText(CONCAT('SRID=4326;POINT(', long::text, ' ', lat::text, ')'))
  9. $$;
  10. CREATE TABLE driver_orders (
  11. id SERIAL PRIMARY KEY,
  12. driver_id INTEGER NOT NULL,
  13. address_from VARCHAR NOT NULL,
  14. address_to VARCHAR NOT NULL,
  15. active BOOLEAN DEFAULT true,
  16. date DATE NOT NULL,
  17. longitude_from DOUBLE PRECISION NOT NULL, -- want to omit
  18. latitude_from DOUBLE PRECISION NOT NULL, -- want to omit
  19. longitude_to DOUBLE PRECISION NOT NULL, -- want to omit
  20. latitude_to DOUBLE PRECISION NOT NULL, -- want to omit
  21. -- add autogenerated 'location_from' column
  22. location_from GEOGRAPHY
  23. GENERATED ALWAYS AS
  24. (create_point_geography(longitude_from, latitude_from))
  25. stored,
  26. -- add autogenerated 'location_to' column
  27. location_to GEOGRAPHY
  28. GENERATED ALWAYS AS
  29. (create_point_geography(longitude_to, latitude_to))
  30. stored
  31. );

As you can see 2 columns are autogenerated based on values of other columns. I want to remove the columns named longitude_from, latitude_from, longitude_to, latitude_to whose values are used in generator function. But I want to keep auto-nenerated columns. So, basically I want columns location_from, location_to be auto-generated with given values, not based on other columns.

Is it possible?

答案1

得分: 1

不可以!你不能直接做你想做的事情。文档 明确指出:

> 生成的列是一种特殊列,它始终从其他列计算得出

然而,你可以在 insert 过程中通过调用相同的函数将结果转换为 GEOGRAPHY 列来获得结果。

  1. create table driver_orders (
  2. id serial primary key,
  3. driver_id integer not null,
  4. address_from varchar not null,
  5. address_to varchar not null,
  6. active boolean default true,
  7. date date not null,
  8. location_from geography not null,
  9. location_to geography not null
  10. );
  11. insert into driver_orders(location_from, location_to , ...)
  12. select create_point_geography(longitude_from, latitude_from)
  13. , create_point_geography(longitude_to, latitude_to)
  14. , ...
  15. );
英文:

NO! You cannot do what you want - at least directly. The documentation clearly indicates this:

> A generated column is a special column that is always computed from
> other columns
.

You can however get the results by making the conversion to a GEOGRAPHY column during the insert by calling the same function.

  1. create table driver_orders (
  2. id serial primary key,
  3. driver_id integer not null,
  4. address_from varchar not null,
  5. address_to varchar not null,
  6. active boolean default true,
  7. date date not null,
  8. location_from geography not null,
  9. location_to geography not null
  10. );
  11. insert into driver_orders(location_from, location_to , ...)
  12. select create_point_geography(longitude_from, latitude_from)
  13. , create_point_geography(longitude_to, latitude_to)
  14. , ...
  15. );

huangapple
  • 本文由 发表于 2023年5月30日 00:46:48
  • 转载请务必保留本文链接:https://go.coder-hub.com/76359035.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定