I SQL Server kan du oprette en skalær brugerdefineret funktion ved hjælp af CREATE FUNCTION
udmelding. En skalær brugerdefineret funktion, også kendt som en skalar UDF, er en brugerdefineret funktion, der returnerer en enkelt værdi.
Denne artikel indeholder eksempler på oprettelse af nogle grundlæggende T-SQL-skalære UDF'er.
Syntaks
Lad os først se på syntaksen til at skabe skalære UDF'er.
Syntaksen for T-SQL skalære UDF'er ser sådan ud:
OPRET [ ELLER ÆNDRING ] FUNKTION [ skemanavn. ] funktionsnavn ( [ { @parameter_navn [ AS ][ type_skema_navn. ] parameter_data_type [ =default ] [ LÆSEKUN ] } [ ,...n ] ] ) RETURERER return_data_type [ MED[ ,...n ] ] [ AS ] BEGIN function_body RETURN scalar_expression END [; ]
Og syntaksen for CLR skalære UDF'er:
OPRET [ ELLER ÆNDRING ] FUNKTION [ skemanavn. ] funktionsnavn ( { @parameter_navn [AS] [ type_skema_navn. ] parameter_data_type [ =default ] } [ ,...n ] ) RETURNERER { return_data_type } [ MED[ ,...n ] ] [AS ] EKSTERNT NAVN [; ]
Delene på <function_option>
for T-SQL-funktioner og <clr_function_option>
for CLR-funktioner giver dig mulighed for at angive indstillinger for UDF. Funktionsmuligheder omfatter tilføjelse af kryptering, skemabinding, en EXECUTE AS
klausul, samt specificering af, hvad der skal gøres, når en NULL-værdi sendes som et argument.
En komplet liste over argumenter og funktionsmuligheder kan findes på Microsofts websted.
Microsoft-dokumentationen indeholder mange detaljer, så de følgende eksempler har til formål at give et hurtigt overblik over nogle almindelige koncepter og muligheder, når du opretter skalære UDF'er.
Eksempel 1 – Basic Scalar UDF
Her er et eksempel på koden, der blev brugt til at oprette en grundlæggende T-SQL skalar UDF.
OPRET FUNKTION dbo.ufn_discountPrice( @pris DECIMAL(12,2), @rabat DECIMAL(12,2) ) RETURNERER DECIMAL (12,2)ASBEGIN RETUR @pris * (1 - @rabat);END;Denne skalære UDF accepterer to parametre;
@price
og@discount
. Disse sendes ind i funktionen som argumenter, når funktionen aktiveres. Funktionen tager værdien af disse argumenter, udfører en beregning ved hjælp af disse værdier og returnerer derefter den resulterende værdi. I dette tilfælde returneres den nedsatte pris.Eksempel 2 – Aktiver UDF
Når UDF'en er blevet oprettet, kan den aktiveres i T-SQL-koden, når som helst du har brug for den.
Her er et eksempel på at påkalde UDF:
VÆLG dbo.ufn_discountPrice(100, .2) SOM resultat;Resultat
+----------+| Resultat ||--------|| 80,00 |+----------+Eksempel 3 – Forespørgsel efter en tabel
Skalære UDF'er kan også gøre ting som forespørgselsdatabasetabeller.
Her er en, der returnerer antallet af albums i databasen for en given kunstner.
OPRET FUNKTION dbo.ufn_CountAlbums (@ArtistId int) RETURERER smallintAS BEGIN DECLARE @AlbumCount int; SELECT @AlbumCount =COUNT(AlbumId) FROM Albums WHERE ArtistId =@ArtistId; RETURN @AlbumCount;END;Dette er en skalarfunktion, fordi den returnerer en enkelt værdi. Hvis vi ville returnere en liste over albummer, skulle vi bruge en funktion med tabelværdi, fordi funktioner med tabelværdi returnerer dens resultater som et sæt rækker.
Eksempel 4 – Skemabinding
Når du opretter en brugerdefineret funktion, der afhænger af andre objekter i databasen, er det normalt en god idé at skemabinde UDF'en. Skemabinding af UDF sikrer, at der ikke kan foretages ændringer i de underliggende objekter, som potentielt kan påvirke funktionen.
For eksempel vil du ikke være i stand til at slippe en tabel, som en skemabundet UDF bruger i sin definition.
For at skemabinde en UDF skal du bruge
WITH SCHEMABINDING
i sin definition. Du skal også bruge todelte navne for alle objekter, der refereres til i UDF.Her er det forrige eksempel omskrevet, så det er skemabundet:
OPRET FUNKTION dbo.ufn_CountAlbums (@ArtistId int) RETURERER smallintWITH SCHEMABINDINGAS BEGIN DECLARE @AlbumCount int; SELECT @AlbumCount =COUNT(AlbumId) FROM dbo.Albums WHERE ArtistId =@ArtistId; RETURN @AlbumCount;END;Så jeg ændrede to ting fra det første eksempel. Jeg tilføjede
WITH SCHEMABINDING
, og jeg ændredeAlbums
tildbo.Albums
.Hvis nogen nu prøver at droppe den tabel eller foretage andre ændringer i den, får de en fejl.
Eksempel 5 – Kryptering
Du kan også bruge
WITH ENCRYPTION
for at kryptere funktionen.OPRET FUNKTION dbo.ufn_CountAlbums (@ArtistId int) RETURERER smallintMED KRYPTIONER START DECLARE @AlbumCount int; SELECT @AlbumCount =COUNT(AlbumId) FROM dbo.Albums WHERE ArtistId =@ArtistId; RETURN @AlbumCount;END;Eksempel 6 – NULL-input
Når du kalder funktionen, hvis nogen af argumenterne er NULL, udføres funktionens krop stadig. Det vil sige, medmindre du udtrykkeligt har angivet
RETURNS NULL ON NULL INPUT
i funktionens definition.Angivelse af denne indstilling vil returnere NULL, hvis nogen af argumenterne er NULL.
OPRET FUNKTION dbo.ufn_CountAlbums (@ArtistId int) RETURNERER smallintWITH RETURNER NULL PÅ NULL INPUTAS BEGIN DECLARE @AlbumCount int; SELECT @AlbumCount =COUNT(AlbumId) FROM dbo.Albums WHERE ArtistId =@ArtistId; RETURN @AlbumCount;END;Når jeg aktiverer funktionen ved at bruge NULL som argument:
VÆLG dbo.ufn_CountAlbums(NULL) SOM resultat;Jeg får et andet resultat, afhængigt af hvad jeg har angivet for denne mulighed.
Her er resultatet, når funktionen bruger standardindstillingen (
CALLED ON NULL INPUT
):+----------+| Resultat ||--------|| 0 |+----------+Og her er resultatet, når den bruger
RETURNS NULL ON NULL INPUT
:+----------+| Resultat ||--------|| NULL |+----------+Eksempel 7 – Flere muligheder
Du kan adskille flere muligheder med et komma.
Her er et eksempel, der tilføjer både kryptering og skemabinding til funktionen:
OPRET FUNKTION dbo.ufn_CountAlbums (@ArtistId int) RETURERER smallintMED KRYPTERING, SCHEMABINDINGAS BEGYNDER DECLARE @AlbumCount int; SELECT @AlbumCount =COUNT(AlbumId) FROM dbo.Albums WHERE ArtistId =@ArtistId; RETURN @AlbumCount;END;Eksempel 8 – Ændre en funktion
Du kan ændre en skalær UDF ved at erstatte
CREATE
medALTER
.ÆNDRING AF FUNKTION dbo.ufn_CountAlbums (@ArtistId int) RETURERER smallintWITH SCHEMABINDINGAS BEGIN DECLARE @AlbumCount int; SELECT @AlbumCount =COUNT(AlbumId) FROM dbo.Albums WHERE ArtistId =@ArtistId; RETURN @AlbumCount;END;