2010-08-13 7 views
4

J'ai du mal à formuler cette question de manière à ne pas afficher de résultats pour les colonnes calculées indexées persistantes.Microsoft SQL Server traitera-t-il efficacement une colonne calculée non persistante?

Ma question est, si j'ai une table telle que:

CREATE TABLE Customers (
    ID int, 
    Name nvarchar(50), 
    Balance money, 
    HasBalance AS CONVERT(bit, CASE WHEN Balance > 0 THEN 1 ELSE 0 END) 
) 

En supposant qu'il y ait un indice sur l'équilibre, serait le processeur de requêtes SQL traiter efficacement une requête telle que:

SELECT ID, Name, Balance 
FROM Customers 
WHERE HasBalance = 1 

Est-ce que cela va essentiellement "inline" l'expression de la colonne calculée comme si j'avais spécifié le cas directement dans la requête?

Que se passerait-il si l'expression de la colonne calculée se trouvait dans une fonction non-définie par l'utilisateur de schemabound?

EDIT

Mon exemple était pas génial car, comme il est indiqué, la colonne HasBalance ne serait pas une très bonne distribution des données. Mais ignorant un instant l'efficacité de l'index lui-même, le processeur de requête traitera-t-il essentiellement la requête ci-dessus comme indiqué ci-dessous lors de la sélection d'un index et du choix d'un plan d'exécution?

SELECT ID, Name, Balance 
FROM Customers 
WHERE Balance > 0 

Répondre

4

Cela dépend de la répartition des données, en ce moment vous avez seulement 2 valeurs possibles 1 et 0 .... donc à moins que vous avez 99% des données étant une valeur de votre sélectivité sera très pauvre, alors il doit analyser tout l'index pour trouver toutes les valeurs positives ou négatives

Modifier ..... Voici ce qui se passe, vous obtenez une analyse de table

CREATE TABLE Customers (
    ID int, 
    Name nvarchar(50), 
    Balance money, 
    HasBalance AS CONVERT(bit, CASE WHEN Balance > 0 THEN 1 ELSE 0 END) 
) 


insert Customers values(1,'d',100) 
insert Customers values(2,'d',-2) 
insert Customers values(3,'d',-4) 
insert Customers values(4,'d',3) 
insert Customers values(5,'d',5) 

create index ix_test on Customers(Balance) 


SELECT ID, Name, Balance 
FROM Customers 
WHERE HasBalance = 0 

set showplan_text on 

| --Table scan (OBJET : ([maître]. [dbo]. [Clients]), OERE: (CONVERT (bit, CAS QUAND [maître]. [dbo]. [Client . S] [Balance]> (0,0000 $) ALORS (1) AUTRE (0) FIN, 0) = [@ 1]))

jeter un oeil à ce

SELECT Balance 
FROM Customers 
WHERE HasBalance = 0 

- Index Scan (OBJET: ([maître]. [Dbo]. [Clients]. [Ix_test]), O WH: (CONVERT (bit, CAS QUAND [maître]. [Dbo]. [Clients]. [Balance]> (0,0000 $) ALORS (1) AUTRE (0) FIN, 0) = [@ 1]))

SELECT Balance 
FROM Customers 
WHERE Balance > 0 

| - Index Seek (OBJET: ([maître]. [Dbo]. [Clients]. [Ix_test]), SEEK: ([maître]. [Dbo]. [Clients]. [Balance]> CONVERT_IMPLICIT (argent, [@ 1], 0)) COMMANDES FORWARD)

+0

J'ai mis à jour ma question pour ajouter plus de contexte et dans ce temps je vois que vous avez assez lu mon esprit avec votre édition. Il semblerait donc que les deux requêtes ne seront pas traitées de la même manière. – Josh