sql – 如何在Sybase ASE中模拟GREATEST()?

大多数数据库都有类似于
GREATEST的功能,有时可能很有用.至少这些数据库没有这样的功能:

>德比
> SQL Server
> Sybase ASE
> Sybase SQL Anywhere

对于SQL Server和Sybase SQL Anywhere,可以使用子查询和UNION ALL模拟该函数,如this question here中所示.示例:

-- SELECT GREATEST(field1, field2, field3) FROM my_table
SELECT (SELECT MAX(c) FROM 
                     (SELECT my_table.field1 AS c UNION ALL 
                      SELECT my_table.field2      UNION ALL
                      SELECT my_table.field3) T) AS greatest
FROM my_table

但这在Sybase ASE中不起作用.显然,子查询无权访问外部查询的my_table引用.我得到的错误是

The column prefix ‘my_table’ does not match with a table name or alias name used in the query. Either the table is not specified in the FROM clause or it has a correlation name which must be used instead

请注意,Sybase SQL Anywhere不会出现此问题.知道这里有什么问题以及如何重新编写查询?

我想避免

>存储函数,因为我可能没有必要的授权来创建它们
>冗长的CASE表达式,因为当n是GREATEST的参数数量时,嵌套CASE表达式所需的所有比较的组合排列的表达式长度至少为O(n ^ 2)

最佳答案 据我了解,逻辑(忽略空值)是

SELECT CASE 
          WHEN field1 >= field2 
               AND field1 >= field3
             THEN field1
          WHEN field2 >= field3
             THEN field2
          ELSE field3
       END AS greatest
  FROM my_table;

…但只应在所有值为null时返回null.

我认为这更像是我希望能够做的事情(尽管,Sybase ASE不支持公共表表达式):

WITH my_table
     AS 
     (
      SELECT * 
        FROM (
              VALUES ('A', 1, 2, 3), 
                     ('B', 2, 3, 1), 
                     ('C', 3, 1, 2),
                     ('D', NULL, 2, 3), 
                     ('E', NULL, NULL, 3), 
                     ('F', NULL, 3, NULL), 
                     ('G', 1, NULL, 3), 
                     ('H', 1, 3, NULL), 
                     ('X', NULL, NULL, NULL)
             ) AS T (ID, field1, field2, field3)
     ), 
     T1
     AS
     (
      SELECT ID, field1 AS field_n
        FROM my_table
      UNION
      SELECT ID, field2 AS field_n
        FROM my_table
      UNION
      SELECT ID, field3 AS field_n
        FROM my_table
     )        
SELECT ID, MAX(field_n) AS greatest
  FROM T1
 GROUP 
    BY ID;
点赞