Getting database name from table name in SQL Server - sql-server

I need to get database name from table names in SQL Server. I can query 'tablenames' in the database, but how do I get the database name for each table as well?
select *
from sys.tables;
Output:
name object_id principal_id schema_id parent_object_id type type_desc create_date modify_date is_ms_shipped is_published is_schema_published lob_data_space_id filestream_data_space_id max_column_id_used lock_on_bulk_load uses_ansi_nulls is_replicated has_replication_filter is_merge_published is_sync_tran_subscribed has_unchecked_assembly_data text_in_row_limit large_value_types_out_of_row is_tracked_by_cdc lock_escalation lock_escalation_desc is_filetable is_memory_optimized durability durability_desc temporal_type temporal_type_desc history_table_id is_remote_data_archive_enabled is_external
DL_CONLog 719055 NULL 1 0 U USER_TABLE 43:24.3 01:41.0 0 0 0 0 NULL 10 0 1 0 0 0 0 0 0 0 0 0 TABLE 0 0 0 SCHEMA_AND_DATA 0 NON_TEMPORAL_TABLE NULL 0 0
DL_TIMJobImportLinkBrokerToModule 771110 NULL 1 0 U USER_TABLE 45:12.1 45:20.7 0 0 0 1 NULL 64 0 1 0 0 0 0 0 0 0 0 0 TABLE 0 0 0 SCHEMA_AND_DATA 0 NON_TEMPORAL_TABLE NULL 0 0

Try using
SELECT * FROM INFORMATION_SCHEMA.TABLES

sys.tables gives you list of table of current database. The current database name can be query from db_name().
If you are looking for a list of tables of a specific database, use db1.sys.tables
Not really sure what is your requirement, but if you want current database & table name, you can query INFORMATION_SCHEMA.TABLES

Related

Combine like rows in table that used count function in the select

I am writing a query to access health information from my student information system for state and county record compliance. We are using SQL Server 2000 (legacy system) as the backend. The query is this:
select
i.Description Immunization,
Case
When si.Exempt = 'P' Then Count (LName)
Else 0
END AS 'Personal Exempt',
Case
When si.Exempt = 'M' Then Count (LName)
Else '0'
END AS 'Medical Exempt',
Case
When si.Exempt = 'R' Then Count (LName)
Else 0
END AS 'Religious Exempt',
Case
When si.Exempt = 'I' Then Count (LName)--AS 'Personal Exemption'
Else '0'
END AS 'Had Illness'
from student cross join immunization i left join StImmunization si on si.sno = Student.sno and si.immcode = i.code
where Student.Status = 'A' and i.TotalReq > 0
Group BY i.Description, si.exempt
The output is this:
Immunization PersonalExempt MedicalExempt RelgiousExempt HadIllness
Chicken pox (Varicella) 0 0 0 6
Chicken pox (Varicella) 1 0 0 0
Hepatitis B 1 0 0 0
T_DAP 0 0 0 0
Polio 0 0 0 0
Diptheria, Tetanus,
Pertussis 0 0 0 0
Hepatitis B 0 0 0 0
Diptheria, Tetanus,
Pertussis 0 0 0 0
MMR 0 0 0 0
T_DAP 1 0 0 0
MMR 1 0 0 0
Polio 1 0 0 0
Chicken pox (Varicella) 1 0 0 0
I would like the output to combine the like rows of the columns so it looks like this and if necessary add like row and columns:
Imunization PersonalExempt Medical Exempt Religious Exempt Had Illness
Chicken pox (Varicella) 2 0 0 6
Hepatitis B 1 0 0 0
T_DAP 1 0 0 0
Polio 1 0 0 0
Diptheria, Tetanus,
Pertussis 1 0 0 0
Notice row one (below) is the sum of rows 2 and 13 (above). Any ideas on how to accomplish this?
Better to use SUM here -- then you can select a 1 or 0 to make the sum give the count.
Old SQL GROUP BY trick.
select
i.Description AS Immunization,
SUM(Case When si.Exempt = 'P' Then 1 Else 0 END) AS 'Personal Exempt',
SUM(Case When si.Exempt = 'M' Then 1 Else 0 END) AS 'Medical Exempt',
SUM(Case When si.Exempt = 'R' Then 1 Else 0 END) AS 'Religious Exempt',
SUM(Case When si.Exempt = 'I' Then 1 Else 0 END) AS 'Had Illness'
from student cross join immunization i left join StImmunization si on si.sno = Student.sno and si.immcode = i.code
where Student.Status = 'A' and i.TotalReq > 0
Group BY i.Description

In SQL Server, Split bit column to 2 columns using PIVOT

I have a table as below
Name Grade SubjectAorB
Pooja B 1
Preeti C 0
Preeti C 1
Chintu A 1
Deepika B 0
Deepika B 1
Peter A 0
John A 0
Last column SubjectAorB has values as 0 and 1. 0 means Subject A and 1 means Subject B. A student can have either of the subject or both. I want output as below:
Name Grade Subject A Subject B
Pooja B 0 1
Preeti C 1 1
Chintu A 0 1
Deepika B 1 1
Peter A 1 0
John A 1 0
You can do this using conditional aggregation:
SELECT
Name,
Grade,
SubjectA = MAX(CASE WHEN SubjectAorB = 0 THEN 1 ELSE 0 END),
SubjectB = MAX(CASE WHEN SubjectAorB = 1 THEN 1 ELSE 0 END)
FROM #tbl
GROUP BY Name, Grade

Formulating Code and SQL Query

I have a Table in DB named 'Retail'
CustomerID Itemset
1 1
1 3
1 7
2 6
2 7
3 4
... ...
I want to write this table in Datatable 'Matrix' where the Rows are Itemset={1,2,3,4,5,6....,k} and Columns are CustomerID={1,2,3,4,...,x}
and the rows are 1 if the 'Itemset' belongs to the CustomerID.
The output I want is like..
1 2 3 4 5 6 7 ............. x
1 1 0 1 0 0 0 1 0 0 0 0 0 0 0 0
2 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0
3 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0
4
5
6 /And so on!
7
8
9
`
I tried to code it but the problem is in VS Parameters for SQL Query don't work with Loops.
This is my code-
objConnection.Open()
Dim matrix As DataTable = New DataTable("Retail")
intcount = 0
For intcount = 1 To noofCustomerID_col
matrix.Columns.Add(intcount, GetType(Integer))
Next
Dim i As Integer
Dim workRow As DataRow
Dim Boolin As Boolean
For i = 1 To 9
ObjCommand.CommandText = "Select count(*) from Retail Where CustomerID=#in and Itemset=#in"
ObjCommand.Parameters.AddWithValue("#in", i) {{I Get Error here as I can't Loop Parameters}}
Boolin = ObjCommand.ExecuteScalar()
workRow = matrix.NewRow()
workRow(0) = i
workRow(1) = Boolin
matrix.Rows.Add(workRow)
Next
Kindly Help. I know this code can completely be wrong and it's okay if you can suggest totally different way of doing it. I've been stuck for quite some time now! Thanks.
If any clarification is needed I shall explain as many times needed in the comments.
Like Tab Alleman suggested, SQL PIVOT can come handy here.
Dynamic SQL is also needed.
DECLARE #DynamicColumn NVARCHAR(MAX),
#DynamicQuery NVARCHAR(MAX)
SELECT #DynamicColumn = SELECT '[' + CONVERT(NVARCHAR, CustomerID) + '],'
FROM Retail AS Customer
ORDER BY CustomerID
FOR XML PATH('')
SELECT #DynamicColumn = SUBSTRING(#DynamicColumn, 0, DATALENGTH(#DynamicColumn) / 2)--REMOVE EXTRA ","
SELECT #DynamicQuery = 'SELECT *
FROM ( SELECT CustomerID,
ItemSet
FROM Retail) AS D
PIVOT
(
COUNT([CustomerID])
FOR Itemset IN (' + #DynamicQuery + ')
) AS P'
EXECUTE(#DynamicQuery)

SQL Server Rebulid Index is not completely?

I just have a question about rebuild index.
After I had rebuilt the index, I found the physical order of pages is not completely "in order", I saw the pages which has small PID's is after the page has big PID's, as below, the page 7234 is after 23596, this is why. Why is the PID after building the index not in order from small to big or from big to small?
objectID PagePID PrePagePID NextPagePID
93243387 23590 0 0 10 NULL
93243387 7440 23583 0 2 1
93243387 7441 0 0 2 2
93243387 23583 0 7440 2 1
93243387 23589 0 23591 1 0
93243387 23591 23589 23592 1 0
93243387 23592 23591 23593 1 0
93243387 23593 23592 23594 1 0
93243387 23594 23593 23595 1 0
93243387 23595 23594 23596 1 0
93243387 23596 23595 7432 1 0
93243387 7432 23596 7433 1 0 <---------
93243387 7433 7432 7434 1 0
93243387 7434 7433 7435 1 0
93243387 7435 7434 7436 1 0
Try to run the following command just replace 'MyTable' with your tablename and verify if index is indeed fragmented.
SELECT DB_NAME(database_id) AS [Database Name]
,OBJECT_NAME(ps.OBJECT_ID) AS [Object Name]
,i.name AS [Index Name]
,ps.index_id
,ps.index_type_desc
,ps.avg_fragmentation_in_percent
,ps.fragment_count
,ps.page_count
,i.fill_factor
,i.has_filter
,i.filter_definition
FROM sys.dm_db_index_physical_stats(DB_ID(), NULL, NULL, NULL, 'LIMITED') AS ps
INNER JOIN sys.indexes AS i WITH ( NOLOCK )
ON ps.[object_id] = i.[object_id]
AND ps.index_id = i.index_id
WHERE database_id = DB_ID()
AND OBJECT_NAME(ps.OBJECT_ID) = 'MyTable'
ORDER BY avg_fragmentation_in_percent DESC
OPTION ( RECOMPILE );
after than reogranize all indexes on that table and after rebuild it.
Organize syntax
-- Reorganize all indexes on the HumanResources.Employee table.
ALTER INDEX ALL ON HumanResources.Employee
REORGANIZE ;
GO
Rebuild syntax:
ALTER INDEX PK_Employee_BusinessEntityID ON HumanResources.Employee
REBUILD;
GO
after all that rerun the first query.

Partition data into subgroups based on bit fields

I have the first 4 columns of data, and I wan't to use the Ranking functions in the SQL 2008 R2 to derive the fifth column. What's the best way to partition the data into subgroups based on the nextiteminsubgroup and previousiteminsubgroup fields?
Group OrderInGroup NextItemInSubGroup PreviousItemInSubGroup SubGroup
1 1 1 0 1
1 2 1 1 1
1 3 1 1 1
1 4 0 1 1
1 5 0 0 2
1 6 0 0 3
1 7 1 0 4
1 8 1 1 4
1 9 0 1 4
2 1 0 0 1
2 2 0 0 2
2 3 0 0 3
2 4 1 0 4
2 5 0 1 4
3 1 0 0 1
4 1 0 0 1
4 2 0 0 2
4 3 0 0 3
A recursive CTE solution:
DECLARE #t TABLE
([Group] INT
,OrderInGroup INT
,NextItemInSubGroup INT
,PreviousItemInSubGroup INT
,SubGroup INT
)
INSERT #t
VALUES
(1,1,1,0,1),(1,2,1,1,1),(1,3,1,1,1),(1,4,0,1,1),(1,5,0,0,2),(1,6,0,0,3),
(1,7,1,0,4),(1,8,1,1,4),(1,9,0,1,4),(2,1,0,0,1),(2,2,0,0,2),(2,3,0,0,3),
(2,4,1,0,4),(2,5,0,1,4),(3,1,0,0,1),(4,1,0,0,1),(4,2,0,0,2),(4,3,0,0,3)
;WITH recCTE
AS
(
SELECT [Group], OrderInGroup,NextItemInSubGroup , PreviousItemInSubGroup, 1 AS subgroup
FROM #t
WHERE OrderInGroup = 1
UNION ALL
SELECT r.[Group], t.OrderInGroup,t.NextItemInSubGroup , t.PreviousItemInSubGroup,
CASE WHEN r.NextItemInSubGroup = 1 THEN r.subgroup ELSE r.subgroup + 1 END
FROM recCTE AS r
JOIN #t AS t
ON t.[Group] = r.[Group]
AND t.OrderInGroup = r.OrderInGroup + 1
)
SELECT * FROM recCTE
ORDER BY [Group],OrderInGroup ;
P.S. it's best practice to avoid using SQL keywords (e.g. GROUP) as table/column names
Seems like 0 and 0 restart the ranking.
Select
Rank() Over (
Partition By
[Group]
, Case When [NextItemInSubGroup] + [PreviousItemInSubGroup] = 0
Then 0
Else 1
End
Order By [OrderInGroup]
) as [SubGroup]
From Your_Table;

Resources