在Oracle10g中有条件地选择多个列

时间:2011-11-11 20:03:21

标签: sql oracle oracle10g

我有一张桌子,里面有十几个不同的栏目。有没有办法根据某种条件有条件地选择列?

例如,我们会说这是一个包含用户名,密码,所有内容的用户表,以及一个包含该用户登录失败次数的字段。 (密码错误,用户名正确)。因此,当用户名或密码错误时,或者只是在用户名正确的情况下返回所有内容的查询时,我不希望查询返回任何内容,我希望查询在用户名正确但密码错误时返回子集。

伪SQL:

SELECT column1,
       column2,
       column3,
       column4,
       column5,
       column6,
   --If this condition is not met the following columns are not selected
   IF password = password  
   (
       conditional_column1,
       conditional_column2,
       conditional_column3
   )
FROM source_table
WHERE username = username

我已经尝试了CASE语句和DECODE,但每个语句只为每个条件返回一个值。我想为单个条件选择几个列。

我无法访问PL / SQL,我试图将这一切保留在一个查询中。有人知道这是否可行?

修改

只是为了澄清,在我的情况下,我不想检查我是否要求用户名,我想检查是否有任何行username = x。如果我所要做的就是将username传递给函数并构建一个查询字符串,这不会有问题。

所以流程如下:
获取一些用户名为'x'的列,如果密码为'y',则获取其他列。

3 个答案:

答案 0 :(得分:2)

Justin是正确的,没有办法(除了SELECT *或像PIVOT这样的衍生物)从静态查询中获取可变数量的列。我的2条建议是:

  1. 动态SQL,如果您可以控制查询的创建方式。

  2. 确定最大列数,并使用CASE / DECODE在您的source_table上抛出一个视图,就像您尝试过的那样。如果空检查不够,则可以为每个条件列添加指示符列。我已经用它来成功解决“无法查询未知域名问题”的问题。

答案 1 :(得分:2)

听起来您想要了解oracle的虚拟专用数据库(VPD)功能

答案 2 :(得分:0)

将查询提交给SQL引擎时,必须知道要选择的列数。 SQL引擎不能让列数在运行时变化。

但是,您可以使用动态SQL来组合将动态提交给SQL引擎的查询。例如,我可以创建一个PL / SQL过程,它将动态组合包含不同列的SQL语句,并将SYS_REFCURSOR返回给调用者。您可以使用您的应用程序使用的任何语言执行类似的操作。

SQL> create or replace procedure dyn_emp( p_include_empno in boolean,
  2                                       p_rc           out sys_refcursor )
  3  as
  4    l_sql varchar2(1000);
  5  begin
  6    l_sql := 'SELECT ename ';
  7    if( p_include_empno )
  8    then
  9      l_sql := l_sql || ', empno ';
 10    end if;
 11    l_sql := l_sql || ' from emp';
 12    open p_rc for l_sql;
 13  end;
 14  /

Procedure created.

SQL> variable rc refcursor;
SQL> exec dyn_emp( true, :rc );

PL/SQL procedure successfully completed.

SQL> print rc

ENAME           EMPNO
---------- ----------
SMITH            7369
ALLEN            7499
WARD             7521
JONES            7566
MARTIN           7654
BLAKE            7698
CLARK            7782
SCOTT            7788
KING             7839
TURNER           7844
ADAMS            7876
JAMES            7900
FORD             7902
MILLER           7934

14 rows selected.

SQL> exec dyn_emp( false, :rc );

PL/SQL procedure successfully completed.

SQL> print rc

ENAME
----------
SMITH
ALLEN
WARD
JONES
MARTIN
BLAKE
CLARK
SCOTT
KING
TURNER
ADAMS
JAMES
FORD
MILLER

14 rows selected.