Bru Medishetty's SeekWell Blogs
Posts tagged Performance Tuning
My First Article in MSSQLTips
Feb 11th
Today is a special day for me. An article that I submitted is published in MSSQLTips. The article looks into the Index fill factor settings and what is a good value for a given scenario.
Continue to read the article Understanding SQL Server Index Fill Factor Setting.
– Bru Medishetty
Performance Tuning in SQL Server
Jan 5th
One of the frequently asked questions in forums, interviews and during general discussions, is performance tuning. In fact, a friend of mine, (who knows a little bit of SQL Server) when speaking about my blogs, asked me why I had not written any blog on performance tuning. I gave a pause and said, do you know that heavy usage of cursors result in poor performance, Database partitioning results in slightly better performance and Database Snapshots cause a performance overhead? Then I continued, though you see I had a blog on those topics, it is not noticed that they are related to performance of the SQL Server.
The point is, there are many actions or the usage of certain features which directly or indirectly affect the performance of a SQL Server. I would like to post blogs on performance tuning SQL Server, it may be Query Tuning such as rewriting the query to perform better or looking at Indexes and ensure that there are proper Indexes that help the query. It can be related to locking / blocking happening on the database or improper settings of the database options.
There are certain other things to look at when looking to tune a SQL Server apart from those mentioned above. An improper placement of the database files can lead a performance degradation or excessive usage of cursors. There can be system bottlenecks such as Memory, Processor, Disk or Network that is the prime cause for a system slowness.
Many of these shall be addressed individually in the forth-coming blogs.
– Bru Medishetty
Enable AWE Option in SQL Server
Nov 16th
In this article we will look at the steps to enable AWE Option in SQL Server. When enabled, the Advanced Windowing Extensions gives the ability to SQL Server to utilize Memory more than 4 GB. AWE enabling for SQL Server is valid in 32 Bit Systems only, on 64 bit systems AWE is not required to be enabled.
Steps to enable AWE
In the SSMS, right click on the SQL Instance in Object Explorer, and select properties. the following Properties Dialog Box is displayed.
In the left Pane of the Box, Select the Memory Page and Under Server Memory options check the box as shown in the picture below to use AWE to allocate memory. You can also specify a Minimum and Maximum Memory SQL Server can utilize on the machine. So that incase of Memory available to SQL Server it does not complete utilize and resulting in no or less memory to the Operating System and other application running on the Server.
Select OK in the Properties page. The change in the setting will not be effective upon restarting SQL Server.
Alternately, you can also enable using sp_configure. The following scripts provide the alternate steps to
perform to enable AWE option.
As always, I suggest referring other technical information before enabling AWE and other system settings that need to be enabled on the Server for this to be successful, such as enabling /3GB switch or /pae switch in Boot.ini etc.
–Bru Medishetty
Cursors in SQL Server
Nov 12th
Cursors in SQL Server enable you to work with each of records in a record set, so that you can sequentially work with those records and carry out the required task.
The best example that I can recollect to quote here is when you have a table with 100 rows, with one of the columns as email address. You are required to send an email to all valid records in that column and each record is some way or the other has its own condition, then a Cursor would be a good way to implement this.
What cursor does is, it enables you to fetch the data into the memory and then for each of the row in the data set, you can look at the row, can implement any custom logic that is needed and move on to the next row until you reach the end of the records.
There are different types of cursors available and based on the one you choose, you can actually move back and forth with the records.
One other example I can give is, when you need to run a backup for all the databases in a SQL Instance, it is very easy to implement using cursors and has been used by me and many SQL DBA’s before the introduction of the DTS and SSIS technologies.
That is the main benefit of cursors, but the flip side to it is, they are avoided in situations where the dataset is large, due to performance issues with cursors. Since they have this unique ability to traverse through the dataset, they occupy a high amount of memory in the Server.
You should be able to find many examples on this topic and I shall try to publish an article with more details in one of my next blogs.
–Bru Medishetty
Database Partitioning in SQL Server 2005
Sep 18th
I would like to explain the steps involved in implementing Database Partitioning in SQL Server 2005. If you had already implemented Very Large Databases using federated Databases, you would be relieved that Database Partitioning is very easy to configure and work with and the pain to maintain is gone with this wonderful feature.
Implementing Database Partitioning involves mainly 3 Steps.
- Creating a Partition Function
- Creating a Partition Scheme
- Creating a Partitioned Table or Index
Creating Database to setup Partitioning
USE [master]
GO
CREATE DATABASE [LearnSQLwithBru] ON PRIMARY
( NAME = N‘LearnSQLwithBruData1′,FILENAME = N‘E:\LearnSQLwithBruData1.mdf’ ,SIZE = 3072KB , MAXSIZE = UNLIMITED, FILEGROWTH = 1024KB ),
FILEGROUP [Filegroup_Sep2009]
( NAME = N‘LearnSQLwithBruData2′,FILENAME = N‘E:\LearnSQLwithBruData2.ndf’ ,SIZE = 3072KB , MAXSIZE = UNLIMITED, FILEGROWTH = 1024KB ),
FILEGROUP [Filegroup_Oct2009]
( NAME = N‘LearnSQLwithBruData3′,FILENAME = N‘E:\LearnSQLwithBruData3.ndf’ ,SIZE = 3072KB , MAXSIZE = UNLIMITED, FILEGROWTH = 1024KB )
LOG ON
( NAME = N‘LearnSQLwithBru_log’,FILENAME = N‘E:\LearnSQLwithBru_log.ldf’ ,SIZE = 10240KB , MAXSIZE = 2048GB , FILEGROWTH = 10%)
GO
Step 1 : Creating a Partition Function
You must identify the Column which would be used to partition the Database. In this example I am partitioning the Database using the Datetime Value, so that we can use large Tables / Indexes on those Large tables to use this Partition. There would a good deal of benefit if the Partitioning is used by both a Large Table and the Indexes on that table. To make things better, while creating the Database, consider placing the Data Files in the Filegroups on Different Disk Drives. With or without Partitioning, SQL Server has a better performance when a Database is created with multiple Disk Drives and with Multiple Filegroups.
Follow the Code below to create a Partition Function which is based on a Datetime Values, so this gives you an opportunity to partition all the Large Tables in the current Database to be portioned by the month.
USE LearnSQLWithBru
GO
CREATE PARTITION FUNCTION PF_RangePartition(Datetime)
AS RANGE LEFT FOR
VALUES
(‘20090930 23:59:59.997′,
‘20091031 23:59:59.997′ )
The above script ensures that we are going to create a Partitioning function in which the Range values are used in left justification, so that all the date values left of “20090930 23:59:59.997″ i.e, less than or equal to Sep 30 2009 will be stored as a single range, and then values between Oct 1 2009 to Oct 31 2009 will be stored as separate Range and all the values from Nov 1 2009 will be stored as a Separate range, by SQL Server when implemented later on.
Step 2 : Creating a Partition Scheme
The following code creates a Partition Scheme which will bind the partition Function to Separate Filegroups. Note it is not necessary that you need to have multiple partitions, it ensures in better Performance of the Database if implemented with multiple Filegroups.
CREATE PARTITION SCHEME OrderDateRangePScheme
AS PARTITION PF_RangePartition TO ([Filegroup_Sep2009], [Filegroup_Oct2009], [PRIMARY] )
The script above ensures that all the tables that are going to be created on this partition, will be physically stored based on the Filegroups mentioned. So the Data which has the values below Sep 30 2009 will all be stored separately on the Filegroup_Sep2009, and the values between Oct 1 2009 to Oct 31 2009 will be stored on the Filegroup_Oct2009, and finally any data that is Greater than or Equal to Nov 1 2009 will be stored on the Primary Filegroup.
Step 3 : Creating a Partitioned Table
In Order to create a table which will use the created partitions, we need to mention the partition Name in the create table script as described below.
CREATE TABLE [DBO].[OrderDetails](
[CustomerNo] [INT]NULL, [OrderNo] [NVARCHAR](20) NULL,
[OrderQty] [SMALLINT] NULL, [OrderDate] [DATETIME] NOT NULL)
ON OrderDateRangePScheme (OrderDate)
Inserting Data into the Table
Insert some records in the Table using the following script to check the usage of Partitioning.
INSERT INTO [dbo].[OrderDetails]VALUES (1,‘Ord1′, 1, ‘09/1/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (2,‘Ord2′, 3, ‘09/5/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (3,‘Ord3′, 7, ‘09/10/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (4,‘Ord4′, 2, ‘09/30/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (5,‘Ord5′, 10, ‘10/1/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (6,‘Ord6′, 9, ‘10/10/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (7,‘Ord7′, 6, ‘10/20/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (8,‘Ord8′, 8, ‘11/30/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (9,‘Ord9′, 7, ‘12/1/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (10,‘Ord10′, 3, ‘12/10/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (10,‘Ord10′, 3, ‘12/15/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (10,‘Ord10′, 3, ‘12/20/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (10,‘Ord10′, 3, ‘12/25/2009′)
INSERT INTO [dbo].[OrderDetails]VALUES (11,‘Ord11′, 4, ‘1/20/2010′)
Verifying the Partition Information
Using the sys.partitions view we can check whether the partitions have been storing the records as desired by us.
SELECT * FROM sys.partitions
WHERE OBJECT_NAME(OBJECT_ID)=‘OrderDetails ‘;
Points to be noted
- Only Enterprise Edition supports this feature
- A Partitioning Function can be used by the objects in the same Database.
- A table can have a Maximum of 1000 partitions.
- A Partition Scheme can be defined on 1 or more Filegroups. It is not necessary to have multiple Filegroups.
– Bru Medishetty

Recent Comments