tags:

views:

982

answers:

5

How do I select few columns in a table that only contain NULL values for all the rows? Suppose if Table has 100 columns, among this 100 columns 60 columns has null values. How can I write where condition to check if 60 columns are null.

+4  A: 

where c1 is null and c2 is null ... and c60 is null

shortcut using string concatination (Oracle syntax):

where c1||c2||c3 ... c59||c60 is null

ammoQ
That last bit unfortunately relies on the braindead Oracle inability to tell the difference between an empty string and NULL. It is not a good solution.
paxdiablo
But I'm going to vote you up as the first bit is the right way to do it, sans any possibility of refactoring the DB table.
paxdiablo
If its SQL Server, could use coalesce...
Naren
And when you use vendor-specific functionality, that vendor gets a grip on your short-and-curlies :-)
paxdiablo
If you DON'T use vendor specific functionality, you still DON'T get portability. No main stream RDBMS that I know of correctly implements ANSI SQL (of any ANSI SQL standard). Besides performance tuning, security design, etc, etc should be based on the exact platform you're on (imho). It's an imperfect world, so I don't try to pretend otherwise...
Dems
If you're going to make blanket assertions @Dems, at least back them up with hard data :-). Even if what you say were true, your comment that you don't get portability is correct only if your code tries to use EVERY feature of SQL. Using an intelligent subset will make it portable everywhere and avoid lock-in. If you're happy with staying with DB2 or MSSQL or MySQL, that's fine, use all the speed-up features you want. But we design for portability because that's what our clients want.
paxdiablo
+6  A: 

maybe with a COALESCE

SELECT * FROM table WHERE coalesce(col1, col2, col3, ..., colN) IS NULL
Jhonny D. Cano -Leftware-
If there's any chance to use an index on any of these fields, you've killed it by putting a function around it.
le dorfier
Yeah, per-row functions are a performance killer on any decent-sized table.
paxdiablo
coalesce only works when all those columns have compatible data types (at least in Oracle it doesn't work for a mix of number, date and varchar columns)
ammoQ
If you're checking 60 columns, index will break down very quickly anyway. Even if each column could only contain "NULL" or "1", there are 2^60 comibinations, (taking a million as 1024*1024, that's 1 million million million combinations) Creating and maintaining that index would be a significant overheard. A computed column or materialised view is the only practical performance tuning (imho)
Dems
That;s why DBAs tune the databases - that's not a one-shot operation, it should be done (or at least checked) frequently. I wouldn't have 60 indexes, I'd be examining RUNSTATS output and table content to see where things could be improved, and then adjusting the indexes to squeeze out maximum grunt.
paxdiablo
A: 

It would help to know which db you are using and perhaps which language or db framework if using one.

This should work though on any database.

Something like this would probably be a good stored procedure, since there are no input parameters for it.

select count(*) from table where col1 is null or col2 is null ...
James Black
A: 

Are you trying to find out if a specific set of 60 columns are null, or do you just want to find out if any 60 out of the 100 columns are null (not necessarily the same 60 for each row?)

If it is the latter, one way to do it in oracle would be to use the nvl2 function, like so:

select ... where (nvl2(col1,0,1)+nvl2(col2,0,1)+...+nvl2(col100,0,1) > 59)

A quick test of this idea:

select 'dummy' from dual where nvl2('somevalue',0,1) + nvl2(null,0,1) > 1

Returns 0 rows while:

select 'dummy' from dual where nvl2(null,0,1) + nvl2(null,0,1) > 1

Returns 1 row as expected since more than one of the columns are null.

John Vasileff
+1  A: 

First of all, if you have a table that has so many nulls and you use SQL Server 2008 - you might want to define the table using sparse columns (http://msdn.microsoft.com/en-us/library/cc280604.aspx).

Secondly I am not sure if coalesce solves the question asks - it seems like Ammu might actually want to find the list of columns that are null for all rows, but I might have misunderstood. Nevertheless - it is an interesting question, so I wrote a procedure to list null columns for any given table:

IF (OBJECT_ID(N'PrintNullColumns') IS NOT NULL)
    DROP PROC dbo.PrintNullColumns;
go
CREATE PROC dbo.PrintNullColumns(@tablename sysname)
AS
BEGIN
    SET NOCOUNT ON;
    DECLARE @query nvarchar(max);
    DECLARE @column sysname;
    DECLARE columns_cursor CURSOR FOR
     SELECT c.name
     FROM sys.tables t JOIN sys.columns c ON t.object_id = c.object_id
     WHERE t.name = @tablename AND c.is_nullable = 1;
    OPEN columns_cursor;
    FETCH NEXT FROM columns_cursor INTO @column;
    WHILE (@@FETCH_STATUS = 0)
    BEGIN
     SET @query = N'
     DECLARE @c int
     SELECT @c = COUNT(*) FROM ' + @tablename + ' WHERE ' + @column + N' IS NOT NULL
     IF (@c = 0)
      PRINT (''' + @column + N''');'
     EXEC (@query);

     FETCH NEXT FROM columns_cursor INTO @column;
    END
    CLOSE columns_cursor;
    DEALLOCATE columns_cursor;
    SET NOCOUNT OFF;
    RETURN;
END;
go
xyzzer