为什么交叉加入横向分解阵列的SDO_GEOMETRY对象中的单个属性?

发布于 2025-02-12 19:48:04 字数 2792 浏览 0 评论 0原文

oracle 18c:

我的映射软件具有一个限制,在该软件中,每个表只能处理单个几何列。如果给定表中有多个几何列,则会丢弃错误。

因此,我想找到一种在表中添加其他几何列的方法,但是将其存储为映射软件无法识别的数据类型,因此它将忽略该列(TBD)。

一个想法是将sdo_geometry存储为 sdo_geometry_array datatype,因为该软件将无法识别SDO_GEOMETRY_ARRAY。我总是只存储一个几何形状。

类似于以下内容:

with data (geom_array) as (
select sdo_geometry_array(sdo_geometry('point(10 20)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(30 40)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(50 60)')) from dual
)
select geom_array from data

GEOM_ARRAY (SQL Developer)
----------------------------------------------
MDSYS.SDO_GEOMETRY_ARRAY([MDSYS.SDO_GEOMETRY])
MDSYS.SDO_GEOMETRY_ARRAY([MDSYS.SDO_GEOMETRY])
MDSYS.SDO_GEOMETRY_ARRAY([MDSYS.SDO_GEOMETRY])

毫不奇怪,当我从数组中选择时,它返回整个数组,而不是sdo_geometry(即使数组中只有一个值)。

因此,我想找到一个 简单/简洁 从数组中提取SDO_GEOMETRY的方法。

我可以使用一个自定义功能,该功能可以按预期工作:

with 
function get_geom_from_array(geom_array sdo_geometry_array) return sdo_geometry is
begin
    return geom_array(1);
end;    
data (geom_array) as (
select sdo_geometry_array(sdo_geometry('point(10 20)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(30 40)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(50 60)')) from dual
)
select
    get_geom_from_array(geom_array)
from   
    data

SDO_GEOM
---------------
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]

或者我可以使用交叉加入外侧

select
    v.*
from   
    data d
cross join lateral (
    select sdo_geometry(sdo_gtype, sdo_srid, sdo_point, sdo_elem_info, sdo_ordinates) as sdo_geom
    from   table(d.sdo_array)
    ) v

SDO_GEOM
---------------
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]

那个交叉加入横向作品,但我不明白为什么它将sdo_geometry分配到其属性组件中:

select
    v.*
from   
    data d
cross join lateral (
    select *
    from   table(d.sdo_array)
    ) v

SDO_GTYPE SDO_SRID SDO_POINT              SDO_ELEM_INFO SDO_ORDINATES
--------- -------- ---------------------- ------------- -------------
     2001     null [MDSYS.SDO_POINT_TYPE]          null          null
     2001     null [MDSYS.SDO_POINT_TYPE]          null          null
     2001     null [MDSYS.SDO_POINT_TYPE]          null          null

因此,我需要从这些属性中重建几何形状,就像此:sdo_geometry(SDO_GTYPE,SDO_SRID,SDO_POINT,SDO_ELEM_INFO,SDO_ORDINATES)

重建SDO_DEOMETRY略有不便。但是,我想了解为什么在十字架上横向上会发生这种情况,而不是在自定义功能中。


问题:

为什么交叉连接到横向将数组的SDO_GEOMETRY对象分解为单个属性? (但是功能没有)

Oracle 18c:

I have mapping software that has a limitation where it can only handle a single geometry column per table. If there are multiple geometry columns in a given table, then it will throw an error.

So, I want to find a way to add an additional geometry column to a table, but store it as a datatype that the mapping software doesn't recognize — so it will ignore that column (TBD).

One idea is to store an SDO_GEOMETRY as an SDO_GEOMETRY_ARRAY datatype, since the software wouldn't recognize SDO_GEOMETRY_ARRAY. I would always only store a single geometry in the array.

Similar to this:

with data (geom_array) as (
select sdo_geometry_array(sdo_geometry('point(10 20)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(30 40)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(50 60)')) from dual
)
select geom_array from data

GEOM_ARRAY (SQL Developer)
----------------------------------------------
MDSYS.SDO_GEOMETRY_ARRAY([MDSYS.SDO_GEOMETRY])
MDSYS.SDO_GEOMETRY_ARRAY([MDSYS.SDO_GEOMETRY])
MDSYS.SDO_GEOMETRY_ARRAY([MDSYS.SDO_GEOMETRY])

Unsurprisingly, when I select from the array, it returns the entire array, not the SDO_GEOMETRY (even though there's only a single value in the array).

So, I want to find an easy/succinct way to extract the SDO_GEOMETRY from the array.

I could use a custom function, which works as expected:

with 
function get_geom_from_array(geom_array sdo_geometry_array) return sdo_geometry is
begin
    return geom_array(1);
end;    
data (geom_array) as (
select sdo_geometry_array(sdo_geometry('point(10 20)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(30 40)')) from dual union all
select sdo_geometry_array(sdo_geometry('point(50 60)')) from dual
)
select
    get_geom_from_array(geom_array)
from   
    data

SDO_GEOM
---------------
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]

Or I could use a CROSS JOIN LATERAL:

select
    v.*
from   
    data d
cross join lateral (
    select sdo_geometry(sdo_gtype, sdo_srid, sdo_point, sdo_elem_info, sdo_ordinates) as sdo_geom
    from   table(d.sdo_array)
    ) v

SDO_GEOM
---------------
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]
[MDSYS.SDO_GEOMETRY]

That CROSS JOIN LATERAL works, but I don't understand why it splits the SDO_GEOMETRY into it's attribute components:

select
    v.*
from   
    data d
cross join lateral (
    select *
    from   table(d.sdo_array)
    ) v

SDO_GTYPE SDO_SRID SDO_POINT              SDO_ELEM_INFO SDO_ORDINATES
--------- -------- ---------------------- ------------- -------------
     2001     null [MDSYS.SDO_POINT_TYPE]          null          null
     2001     null [MDSYS.SDO_POINT_TYPE]          null          null
     2001     null [MDSYS.SDO_POINT_TYPE]          null          null

As such, I need to reconstruct the geometry from those attributes, like this: sdo_geometry(sdo_gtype, sdo_srid, sdo_point, sdo_elem_info, sdo_ordinates).

Reconstructing the SDO_GEOMETRY is slightly inconvenient. But also, I want to understand why that happens in the CROSS JOIN LATERAL, but not in the custom function.


Question:

Why does the CROSS JOIN LATERAL break up the array's SDO_GEOMETRY object into individual attributes? (but the function doesn't)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

记忆里有你的影子 2025-02-19 19:48:04

为什么交叉加入横向将数组的sdo_geometry对象分解成各个属性? (但是功能没有)

交叉加入横向正在对待表收集表达式,就像它是一个对象衍生的表(有效的是),并使用集合的每个对象形成行表,然后列是对象的属性。

该功能将一个对象返回到一行的一列中。它们是非常不同的操作。


如果要获取从表集合表达式组成每一行的对象,请使用 value函数

SELECT v.obj
FROM   data d
       CROSS JOIN LATERAL (
         SELECT VALUE(t) AS obj
         FROM   TABLE(d.sdo_array) t
       ) v

db<>>

Why does the CROSS JOIN LATERAL break up the array's SDO_GEOMETRY object into individual attributes? (but the function doesn't)

CROSS JOIN LATERAL is treating the table collection expression as if it is an object-derived table (which it effectively is) and uses each object of the collection to form a row of a table and then the columns are the attributes of the object.

The function is returning a single object into one column of one row. They are very different operations.


If you want to get the objects that comprise each row from the table collection expression then use the VALUE function:

SELECT v.obj
FROM   data d
       CROSS JOIN LATERAL (
         SELECT VALUE(t) AS obj
         FROM   TABLE(d.sdo_array) t
       ) v

db<>fiddle here

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文