June 26, 2008 at 12:56 pm
Just wondering if anyone ever ran into a situation where they had a very large database (by sheer number of tables) and they wanted to drop all the empty tables?
I can find a number of scripts to do rowcounts, but I cant find any that drop tables where rowcount = 0.
Perhaps this old script on this site could be modified with an IF rowCnt = 0 but unsure if a cursor is the way to go.
Thoughts or ideas or modifications to this script are appreciated.
________________
SET NOCOUNT ON
DECLARE @tableName VARCHAR (255), @sql VARCHAR (300)
CREATE TABLE #temp (TableName VARCHAR (255), rowCnt INT)
DECLARE myCursor CURSOR FAST_FORWARD READ_ONLY FOR
SELECT TABLE_NAME FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_TYPE = 'base table'
OPEN myCursor
FETCH NEXT FROM myCursor INTO @tableName
WHILE @@FETCH_STATUS = 0
BEGIN
EXEC ('INSERT INTO #temp (TableName, rowCnt) SELECT ''' + @tableName + ''' as tableName, count(*) as rowCnt from ' + @tableName)
FETCH NEXT FROM myCursor INTO @tableName
END
SELECT TableName, RowCnt FROM #temp ORDER BY TableName
CLOSE myCursor
DEALLOCATE myCursor
DROP TABLE #temp
June 26, 2008 at 2:04 pm
Did you try the system table, sys.sysindexes?
June 26, 2008 at 2:37 pm
You might also want to make sure there aren't any tables that are referenced by operational code, but which don't have rows at the moment.
For example, I've seen code that uses a "Flags" table. If some process is running, it puts a row in the Flags table. When it's done, it removes that row. When the process starts, it checks if the row already exists, and if it does, it either aborts or raises and error. Useful on certain long-running processes that you really don't want overlap on. (There are potentially better solutions, but this is a valid one.)
That table might not have any rows in it at any given time. But you still better not drop it.
I use "staging tables" for a number of bulk import processes. Data goes into them, gets a bunch of cleaning done on it, then the data is moved to permanent tables and the staging table is truncated. Kind of temp tables that get truncated instead of dropped. Again, those tables very often don't have anything in them, but if I dropped them, it would bring a whole department to a rather abrupt halt.
Just a word of warning. Be sure before you drop. Especially in a production database.
- Gus "GSquared", RSVP, OODA, MAP, NMVP, FAQ, SAT, SQL, DNA, RNA, UOI, IOU, AM, PM, AD, BC, BCE, USA, UN, CF, ROFL, LOL, ETC
Property of The Thread
"Nobody knows the age of the human race, but everyone agrees it's old enough to know better." - Anon
June 26, 2008 at 2:48 pm
- be carefull with sysindexes, because it may have an estimate count.
- adapt your script:
e.g. like this
EXEC ('if 0 = (SELECT count(*) as rowCnt from ['+@schema+'].['+@tableName +']) drop table ['+@schema+'].['+@tableName +']' )
Be carefull when doing this, because some tables may be empty temporarly or only in use during special runs, ...:ermm:
So be sure you have a full script of all definitions in your database !!!
Johan
Learn to play, play to learn !
Dont drive faster than your guardian angel can fly ...
but keeping both feet on the ground wont get you anywhere :w00t:
- How to post Performance Problems
- How to post data/code to get the best help[/url]
- How to prevent a sore throat after hours of presenting ppt
press F1 for solution, press shift+F1 for urgent solution
Need a bit of Powershell? How about this
Who am I ? Sometimes this is me but most of the time this is me
June 26, 2008 at 7:20 pm
You can get an accurate rowcount from sys.indexes if you first run DBCC UpdateUsage(0)
It'll be a lot faster than getting a row count from every table in a database with a "huge" number of tables.
--Jeff Moden
Change is inevitable... Change for the better is not.
June 27, 2008 at 12:39 am
And probably you would be better off by first renaming your tobe obsolete tables, and removing them only a couple of months later
EXEC ('if 0 = (SELECT count(*) as rowCnt from ['+@schema+'].['+@tableName +']) EXECUTE sp_rename ''['+@schema+'].['+@tableName +']'', ''['+@schema+'].['+@tableName +'_Obsolete]'', 'OBJECT' ' )
Be carefull if you have implemented DRI.
Use sp_keys / sp_fkkeys to inspect.
Johan
Learn to play, play to learn !
Dont drive faster than your guardian angel can fly ...
but keeping both feet on the ground wont get you anywhere :w00t:
- How to post Performance Problems
- How to post data/code to get the best help[/url]
- How to prevent a sore throat after hours of presenting ppt
press F1 for solution, press shift+F1 for urgent solution
Need a bit of Powershell? How about this
Who am I ? Sometimes this is me but most of the time this is me
June 27, 2008 at 9:58 am
I took into consideration the update stats and renaming...thanks...and ended up with essentially the code below that seemed to work well enough though in the middle of the running the script I did find output errors twice...not sure what to make of it.
error~~~~~~~~~~~~~
Msg 105, Level 15, State 1, Line 1
Unclosed quotation mark after the character string ''.
code used~~~~~~~~~~~~~~~
DBCC UpdateUsage(0)
go
SET NOCOUNT ON
DECLARE @tableName VARCHAR (255), @sql VARCHAR (300), @counter INT
CREATE TABLE #temp (TableName VARCHAR (255), rowCnt INT)
DECLARE myCursor CURSOR FAST_FORWARD READ_ONLY FOR
SELECT TABLE_NAME FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_TYPE = 'base table'
OPEN myCursor
FETCH NEXT FROM myCursor INTO @tableName
WHILE @@FETCH_STATUS = 0
BEGIN
EXEC ('if 0 = (SELECT count(*) as rowCnt from ['+@tableName +']) EXECUTE sp_rename ''['+@tableName +']'', ''['+@tableName +'_Obsolete]''')
FETCH NEXT FROM myCursor INTO @tableName
END
SELECT TableName, RowCnt FROM #temp ORDER BY TableName
CLOSE myCursor
DEALLOCATE myCursor
DROP TABLE #temp
June 27, 2008 at 3:34 pm
You should probably exclude tables LIKE '%_Obsolete%'.
[font="Times New Roman"]-- RBarryYoung[/font], [font="Times New Roman"] (302)375-0451[/font] blog: MovingSQL.com, Twitter: @RBarryYoung[font="Arial Black"]
Proactive Performance Solutions, Inc. [/font][font="Verdana"] "Performance is our middle name."[/font]
June 30, 2008 at 12:04 am
Run the same script again in one month.
If that results in '%_obsolete_obsolete' tables, that would mean it hasn't been used for a month, so maybe good candidate for cleanup.
Johan
Learn to play, play to learn !
Dont drive faster than your guardian angel can fly ...
but keeping both feet on the ground wont get you anywhere :w00t:
- How to post Performance Problems
- How to post data/code to get the best help[/url]
- How to prevent a sore throat after hours of presenting ppt
press F1 for solution, press shift+F1 for urgent solution
Need a bit of Powershell? How about this
Who am I ? Sometimes this is me but most of the time this is me
June 30, 2008 at 1:39 pm
ALZDBA (6/30/2008)
Run the same script again in one month.If that results in '%_obsolete_obsolete' tables, that would mean it hasn't been used for a month, so maybe good candidate for cleanup.
Actually, that's how I usually do it too.
[font="Times New Roman"]-- RBarryYoung[/font], [font="Times New Roman"] (302)375-0451[/font] blog: MovingSQL.com, Twitter: @RBarryYoung[font="Arial Black"]
Proactive Performance Solutions, Inc. [/font][font="Verdana"] "Performance is our middle name."[/font]
Viewing 10 posts - 1 through 10 (of 10 total)
You must be logged in to reply to this topic. Login to reply
This website stores cookies on your computer.
These cookies are used to improve your website experience and provide more personalized services to you, both on this website and through other media.
To find out more about the cookies we use, see our Privacy Policy