我希望有一个表的列表,其中至少有一个非NULL
个数据条目。
换句话说,我想得到以下列返回至少一个条目的列名:
SELECT DISTINCT column_name FROM table WHERE column_name IS NOT NULL
我尝试了以下内容:
SELECT column_name
FROM information_schema.columns
WHERE table_name = "table_name"
AND EXISTS (
SELECT DISTINCT column_name FROM table_name WHERE column_name IS NOT NULL
)
但是这也会返回所有条目都为NULL
的列名。
那么我如何只获得那些非NULL
条目的列?
答案 0 :(得分:10)
从INFORMATION_SCHEMA.COLUMNS
表创建一个包含您要执行的SQL的字符串,然后从该字符串中prepare a statement执行它。
我们希望构建的SQL看起来像:
SELECT 'column_a'
FROM table_name
WHERE `column_a` IS NOT NULL
HAVING COUNT(*)
UNION ALL
SELECT 'column_b'
FROM table_name
WHERE `column_b` IS NOT NULL
HAVING COUNT(*)
-- etc.
(可以省略WHERE
子句并将COUNT(*)
替换为COUNT(column)
,但我认为对索引列的效率可能较低。)
可以使用以下方法完成:
SET group_concat_max_len = 4294967295;
SELECT GROUP_CONCAT(
' SELECT ',QUOTE(COLUMN_NAME),
' FROM table_name',
' WHERE `',REPLACE(COLUMN_NAME, '`', '``'),'` IS NOT NULL',
' HAVING COUNT(*)'
SEPARATOR ' UNION ALL ')
INTO @sql
FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_SCHEMA = DATABASE()
AND TABLE_NAME = 'table_name';
PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;
在sqlfiddle上查看。
答案 1 :(得分:0)
使用此过程将打印具有至少一个非空行的表的列名。
create or replace procedure list_col_notNull(tblName in varchar2)
as
lv_col_name varchar2(200);
lv_ctr number;
lv_sql varchar2(400);
CURSOR cur_col_name is
SELECT column_name
FROM USER_TAB_COLUMNS U
WHERE table_name = tblName order by column_name asc;
begin
open cur_col_name;
LOOP
FETCH cur_col_name INTO lv_col_name;
EXIT WHEN cur_col_name%NOTFOUND;
lv_sql := 'select count(1) From ' || tblName || ' where ' || lv_col_name || ' is not null' ;
EXECUTE IMMEDIATE lv_sql into lv_ctr;
if lv_ctr > 0
then
dbms_output.put_line(lv_col_name);
end if;