使用返回多个值的函数更新多个列

时间:2012-11-27 06:10:33

标签: sql oracle

我正在尝试使用函数的多个返回来更新表。

我创建了一个TYPE

CREATE OR REPLACE TYPE city_state AS OBJECT
(
  city VARCHAR2(30),
  state VARCHAR2(2)
);
/

我有一个函数返回这种类型的变量。

CREATE OR REPLACE FUNCTION closestcity(lat IN NUMBER, lon IN NUMBER) RETURN city_state IS
...

我需要更新包含城市,州,纬度和经度列的表格。使用lat / lon,我应该调用该函数并使用结果来更新city / state的值。我只想为每一行调用一次函数,并且只需要更新一些行(让我们说city为NULL)

这是我到目前为止所得到的

UPDATE (SELECT * FROM t t1 WHERE city IS NULL)
SET (city, state) = (
                     SELECT newcity.city, newcity.state FROM
                       ( SELECT closestcity(latitude, longitude) newcity
                         FROM t t2
                         WHERE t1.latitude = t2.latitude AND
                               t1.longitude = t2.longitude)
                    );

但是我收到了无效的识别错误。我觉得我太复杂了,对此有什么正确的解决方法?

3 个答案:

答案 0 :(得分:2)

您遇到此错误的原因是Oracle尝试限定newcity select语句中引用的SELECT newcity.city, newcity.state。它找不到对象newcity,因此会抛出错误。如果您确实需要,还可以将内联视图命名为t1。作为@Rene has mentioned,您可以使用表名成功替换它。为此,您可以按如下方式重写更新语句:

UPDATE (SELECT * FROM t t1 WHERE city IS NULL) t1
   SET (city, state) = (
                         SELECT closestcity(latitude, longitude).city 
                              , closestcity(latitude, longitude).state
                           FROM t t2
                          WHERE t1.latitude = t2.latitude 
                            AND t1.longitude = t2.longitude 
                        );

或者简单地说:

UPDATE t t1 
   SET city  = closestcity(latitude, longitude).city 
     , state = closestcity(latitude, longitude).state
where t1.city is null

更新#1

update (select nd.newdata.city  as newcity
             , nd.newdata.state as newstate
             , city
             , state
          from (                             
                 SELECT closestcity(latitude, longitude) newdata
                      , city
                      , state
                   FROM t
                  where city is null
                ) nd
              ) q  
set q.city  = q.newcity
  , q.state = q.newstate 

答案 1 :(得分:0)

语法应为:

UPDATE <table1>
set (<column1>, <column2>) = (select <column1>,<column2> 
                              from <table2> 
                              where <where clause table2 > )
where <where clause table1>

所以你的查询应该是:

UPDATE t1
SET (city, state) = (SELECT closestcity(latitude, longitude) newcity
                            ,state
                       FROM t t2
                      WHERE t1.latitude = t2.latitude 
                        AND t1.longitude = t2.longitude)
where city IS NULL

答案 2 :(得分:0)

只需一次更改

UPDATE (SELECT * FROM t WHERE city IS NULL) **t1**
SET (city, state) = (
                     SELECT newcity.city, newcity.state FROM
                       ( SELECT closestcity(latitude, longitude) newcity
                         FROM t t2
                         WHERE t1.latitude = t2.latitude AND
                               t1.longitude = t2.longitude)
                    );