Oracle
 sql >> Cơ Sở Dữ Liệu >  >> RDS >> Oracle

SQL:Tìm kiếm danh sách các cột với một giá trị nhất định (trong một hàng)

Đây không phải là một phần thông thường của chức năng cơ sở dữ liệu. Tuy nhiên, bạn không phải là người đầu tiên yêu cầu điều này hoặc điều gì đó tương tự.

Giải pháp đòi hỏi hai điều. Đầu tiên là từ điển dữ liệu; cơ sở dữ liệu Oracle không hỗ trợ Reflection nhưng nó đi kèm với một tập hợp các khung nhìn cung cấp cho chúng ta siêu dữ liệu về các đối tượng cơ sở dữ liệu của chúng ta. Trong trường hợp này, chúng tôi cần user_tab_columns , sẽ cung cấp cho chúng tôi các cột cho một bảng nhất định. Điều thứ hai là SQL động; đây là khả năng tập hợp một truy vấn SQL trong thời gian chạy và sau đó thực thi nó. Có một số cách để thực hiện việc này, nhưng thông thường con trỏ tham chiếu là đủ.

Đoạn mã sau đây là một bằng chứng về khái niệm. Nó có bốn tham số:

  1. tên của bảng bạn muốn tìm kiếm
  2. tên của cột khóa chính của bảng đó
  3. giá trị khóa chính mà bạn muốn hạn chế
  4. giá trị bạn muốn tìm kiếm.

Nó còn thô sơ nên bạn có thể cần phải chỉnh sửa nó để làm gọn gàng đầu ra hoặc để làm cho chương trình linh hoạt hơn.

create or replace procedure search_cols
  (tname in user_tables.table_name%type
   , pk_col in user_tab_columns.column_name%type
   , pk in number
   , val in number )
is
    firstcol boolean := true;
    stmt varchar2(32767);
    result varchar2(32767);
    rc sys_refcursor;
begin
    stmt := 'select ';
    << projection >>
    for lrec in ( select column_name from user_tab_columns
                  where table_name = tname
                  and column_name != pk_col
                  and data_type = 'NUMBER'
                  order by column_id )
    loop
        if not firstcol then
            stmt := stmt || chr(10) || '||'',''||';
        else
            firstcol := false;
        end if;
        stmt := stmt || ' case when '|| lrec.column_name||' = '|| val ||
                           ' then '''|| lrec.column_name || ''' else null end';
    end loop projection;
    stmt := stmt || chr(10)|| ' from '||tname||' where '|| pk_col || ' = '|| pk;
    --  dbms_output.put_line(stmt);
    open rc for stmt;
    fetch rc into result;
    close rc;
    dbms_output.put_line(tname || '::' || val || ' found in '||result);
end search_cols;
/

Như bạn có thể thấy, SQL động rất khó đọc. Khó gỡ lỗi hơn :) Vì vậy, bạn nên có một phương tiện để hiển thị câu lệnh cuối cùng.

Dù sao, đây là kết quả:

SQL> set serveroutput on size unlimited
SQL> exec search_cols('T23', 'ID', 111, 10)
T23::10 found in ,COL_B,COL_C,

PL/SQL procedure successfully completed.

SQL> exec search_cols('T23', 'ID', 222, 10)
T23::10 found in COL_A,,,

PL/SQL procedure successfully completed.

SQL>


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Tương thích oci8, php7 và Oracle 10.1

  2. Có một hệ thống kiểm soát phiên bản cho các thay đổi cấu trúc cơ sở dữ liệu không?

  3. Cách xóa tệp nhật ký lưu trữ trên phiên bản AWS RDS Oracle

  4. Không thể chạy truy vấn chọn động lớn trong thủ tục được lưu trữ

  5. cột không null có thể hoãn lại