【问题标题】:Order by in for loop (SQL UDF)在 for 循环中排序 (SQL UDF)
【发布时间】:2013-02-14 07:24:23
【问题描述】:

我想使用 SQL UDF 聚合一些行。我想首先选择按其 id 排序的行,然后将它们连接到逗号分隔的列中。我的函数中的 order by 子句有错误,因为它位于 for 循环内。有没有办法在不删除 order by 子句的情况下运行它?我的数据库是 DB2

CREATE FUNCTION mySchema.getDates(recId INTEGER)
RETURNS VARCHAR(1024)
LANGUAGE SQL
    BEGIN ATOMIC
        DECLARE STR VARCHAR(1024);
        SET STR = '' ;
        LOOP1 : FOR ROW AS (select replace(char(myDate,EUR),'.','/') as myDate from myTable.BookingDates where recId=recId order by rec_crt-id)
        DO
            IF ROW.myDate IS NOT NULL THEN
                SET STR = STR || CAST ( ROW.myDate AS VARCHAR ( 20 ) ) || ', ' ;
            END IF ;
        END FOR;
    RETURN STR ;
END 
SQL State: 42601
Vendor Code: -199
Message: [SQL0199] Keyword ORDER not expected. Valid tokens: ) UNION EXCEPT. Cause . . . . . :   The keyword ORDER was not expected here.

【问题讨论】:

  • ... 为什么要将它作为分隔列?大多数类型的格式化应该在应用层完成。什么版本的 DB2?此外,SQL 通常不应该与循环一起使用,因为大多数引擎都不是为了在这些术语中“思考”而编写的。而EUR 是一种“模糊”格式,在那个月/日可能会出现反转(尤其是在使用“标准”分隔符时)。如果我看到这个输出,我可能会假设美国格式的日期!请注意,这可以通过使用递归 CTE 来完成,尽管我不确定它应该是......
  • @Clockwork-Muse 感谢您的详细回复,我同意您不使用循环的观点,但这是一个愚蠢的要求。要求是一个报告,我必须显示查询已返回的每一行数据的日期。我使用 EUR 将日期格式化为 dd/MM/yyyy 格式(默认情况下它们以 yyyy/dd/MM 存储在数据库中)。
  • @Clockwork-Muse 关于递归,我不想使用递归,因为它容易出错。我也不知道递归 sql 语句的最大级别。
  • @DamienJoe,递归不会比任何其他方法更容易出错。而且实际上你可以走多远没有限制——它不像递归函数调用将东西放在堆栈上。我刚刚测试了一个 10,000,000 级别的递归查询,它运行良好。如果行数很少,使用循环没有任何问题。但是,如果此解决方案太慢,您可能需要查看递归解决方案。
  • 如果myDate 实际上是一个日期/时间戳类型(这是一个可怕 列名),它并不是真正以ISO 格式存储的。如果您已经有行,为什么不能从那里提取日期 - 其余数据如何显示?

标签: sql db2 user-defined-functions


【解决方案1】:

这是行不通的:

where recId=recId

DB2 不会意识到您希望其中一个作为函数参数而另一个作为列名。它将对两者使用相同的,具有返回所有行的效果。您需要将函数参数命名为与列名不同的名称。

除此之外,与上述类似的代码对我来说效果很好。

您是编写函数的新手吗?一个常见错误是将 SQL 编辑器的语句分隔符设置为 ;。这将使它尝试将函数分解为语句,而不是将整个内容作为单个命令发送。它会导致很多语法错误,例如上面的(对不起,如果您已经知道,但我花了一段时间才弄清楚!)。

【讨论】:

  • 感谢您指出这一点。如您所说,我已重命名参数。我对 SQL UDF 相当陌生,我没有在上面的代码中使用分隔符来表示“选择”。您是否指的是每个语句的分隔符?我应该将它们全部删除吗?感谢您的理解...
  • @DamienJoe,你用什么程序来运行这个 SQL 代码?在设置的某处,程序将允许您指定语句分隔符来分隔语句。通常设置为;。您想将该设置更改为其他设置。不要从函数本身中删除分号;这些需要发送到数据库。
猜你喜欢
  • 2022-01-07
  • 2018-09-19
  • 2013-05-25
  • 2013-12-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多