sql >> データベース >  >> RDS >> Oracle

WHERE句にVaryingINリストがあるテーブルからSELECT

    要件はさまざまなINリストと呼ばれます 。 WHERE句の値のINリストの変更を参照してください。

    理由: IN ('1, 2, 3') ない IN (1, 2, 3)と同じ またはIN('1', '2', '3')

    したがって、

    SELECT * FROM temp_id WHERE data_id IN(SELECT ids FROM temp);

    と同じです

    SELECT * FROM temp_id WHERE data_id IN( '1、2、3');

    エラーがスローされます ORA-01722: invalid number -

    SQL> SELECT * FROM temp_id WHERE data_id IN('1, 2, 3');
    SELECT * FROM temp_id WHERE data_id IN('1, 2, 3')
                                           *
    ERROR at line 1:
    ORA-01722: invalid number
    
    
    SQL> SELECT * FROM temp_id WHERE data_id IN(SELECT ids FROM temp);
    SELECT * FROM temp_id WHERE data_id IN(SELECT ids FROM temp)
                                                  *
    ERROR at line 1:
    ORA-01722: invalid number
    

    同じではありません

    SELECT * FROM temp_id WHERE data_id IN(1、2、3);

    正しい出力が得られます-

    SQL> SELECT * FROM temp_id WHERE data_id IN(1, 2, 3);
    
       DATA_ID
    ----------
             1
             2
             3
    

    解決策:

    あなたの要件のために、あなたはこのようにそれを達成することができます-

    SQL> SELECT * FROM temp;
    
    IDS
    --------------------------------------------------------------
    1, 2, 3
    
    SQL> SELECT * FROM temp_id;
    
       DATA_ID
    ----------
             1
             2
             3
             4
             5
    
    SQL> WITH data AS
      2    (SELECT to_number(trim(regexp_substr(ids, '[^,]+', 1, LEVEL))) ids
      3    FROM temp
      4      CONNECT BY instr(ids, ',', 1, LEVEL - 1) > 0
      5    )
      6  SELECT * FROM temp_id WHERE data_id IN
      7    (SELECT ids FROM data
      8    )
      9  /
    
       DATA_ID
    ----------
             1
             2
             3
    

    または、独自のTABLE関数を作成することもできます またはパイプライン関数 これを達成するために。目標は、カンマ区切りのINリストを複数の行に分割することです。 。どのようにそれを行うかはあなた次第です!

    作業デモ

    標準のEMPの例を見てみましょう SCOTTのテーブル スキーマ。

    文字列内のジョブのリストがあり、それらのジョブの従業員をカウントしたい:

    SQL> SET serveroutput ON
    SQL> DECLARE
      2    str VARCHAR2(100);
      3    cnt NUMBER;
      4  BEGIN
      5    str := q'[CLERK,SALESMAN,ANALYST]';
      6    SELECT COUNT(*) INTO cnt FROM emp WHERE JOB IN (str);
      7    dbms_output.put_line('The total count is '||cnt);
      8  END;
      9  /
    The total count is 0
    
    PL/SQL procedure successfully completed.
    

    おー!どうしたの?標準のempテーブルは出力10を提供する必要があります。その理由は、さまざまなINリストであるためです。 。

    正しい方法を見てみましょう:

    SQL> SET serveroutput ON
    SQL> DECLARE
      2    str VARCHAR2(100);
      3    cnt NUMBER;
      4  BEGIN
      5    str := q'[CLERK,SALESMAN,ANALYST]';
      6    SELECT COUNT(*)
      7    INTO cnt
      8    FROM emp
      9    WHERE job IN
     10      (SELECT trim(regexp_substr(str, '[^,]+', 1, LEVEL))
     11      FROM dual
     12        CONNECT BY instr(str, ',', 1, LEVEL - 1) > 0
     13      );
     14    dbms_output.put_line('The total count is '||cnt);
     15  END;
     16  /
    The total count is 10
    
    PL/SQL procedure successfully completed.
    


    1. 結合とサブクエリ

    2. PostgreSQLスキーマのテーブルを一覧表示します

    3. PostgreSQLで現在の日付を取得する方法

    4. 1回のクエリで複数のarray_agg()を呼び出す