0

使用する各フィルターに関連しない多くの列を含む非常に大きな Oracle テーブルがあります。

null値のみを持つ列の名前、またはnullではない列の名前を返すクエリまたは関数をOracleで作成したいと考えています。

4

2 に答える 2

3

常に null の列を見つけたい場合は、このクエリが作成するクエリを実行できます。値が 0 の列は null です。

select 'select ' 
       || listagg('count(' || column_name || ') as ' || column_name, ', ')
           within group (order by column_id)
       || ' from my_table;'
  from user_tab_columns
 where table_name = 'MY_TABLE'

デモ用のSQL Fiddleを次に示します。

列の名前が必要な場合は、PL/SQL を使用する必要があります。この関数は、列名のカンマ区切りのリストを返しますが、もちろんユーザー定義型などを返すこともできます。

create or replace function null_cols( P_TableName varchar2 ) return varchar2 is

   l_cols varchar2(32767);
   l_result number;

begin

   for i in ( select column_name 
                from user_tab_columns
               where table_name = upper(P_TableName)
                     ) loop

      execute immediate 'select count(' || i.column_name || ')
                           from ' || P_TableName
                           into l_result;

      if l_result = 0 then
         l_cols := l_cols || i.column_name || ', ';
      end if;

   end loop;

   return l_cols;

end;
/

これは、関数が追加された同じSQL Fiddleの拡張です。

関数を使用するためにユーザー入力を受け入れる場合は、dbms_assertSQL インジェクションを回避するためにパッケージを使用する必要があることを追加する必要があります。

于 2012-07-15T09:12:24.177 に答える
0

次のクエリを使用して同じものを特定できます。正しい結果を得るために統計を収集するようにしてください

    select table_name, column_name
      from user_tab_cols         
                where table_name = 'MY_TABLE'
       and NUM_DISTINCT = 0
       and NUM_NULLS > 0

更新1: -統計を定期的に収集している場合(100%の統計ではない)、ベンの回答を使用して最適化することもできます。以下は、チェックする必要のある列の数を減らすでしょう

for i in ( select column_name 
            from user_tab_columns
           where table_name = upper(P_TableName)
           and num_distinct=0 and num_nulls > 0
                 ) loop
于 2012-07-15T08:53:24.043 に答える