10 Function
10 Function
1
Outline
Scalar functions in SQL Server
Syntax
Modifying a scalar function
Table variables
Table functions
2
Scalar Functions in SQL Server
Takes as input one or more
parameters, returns a single value
Helps simplify the programmer's code.
For example, if a Select query has a
complex calculation, you can use a
scalar function that encapsulates this
formula, and use it in each query.
3
Syntax to create a function
CREATE FUNCTION [schema_name.]function_name
([@parameter [AS] [type_schema_name.] datatype
[= default] [READONLY]
)
RETURNS return_datatype
[WITH { ENCRYPTION
|SCHEMABINDING
|RETURNS NULL ON NULL INPUT
|CALLED ON NULL INPUT
|EXECUTE AS Clause]
[AS]
BEGIN
[declaration_section]
executable_section
RETURN return_value
END;
4
Description
schema_name: The name of the schema (schema) that
owns the function.
function_name: The name assigned to the function.
@parameter: One or more parameters passed to the
function.
type_schema_name: The data type of the schema (if any).
Datatype: The data type for @parameters.
Default: Default value assigned to @parameter.
READONLY: @parameters cannot be overridden by
functions.
return_datatype: The data type of the return value.
5
Description (cont'd)
ENCRYPTION: The function's source code will not
be stored as text in the system.
SCHEMABINDING: Ensures objects are not
modified to affect the function.
RETURNS NULL ON NULL INPUT: The function will
return NULL if any parameter is NULL.
CALL ON NULL INPUT: The function will execute
even if the parameter is NULL.
EXECUTE AS clause: Defines the security context
to execute the function.
return_value: The value to be returned.
6
Example 1
CREATE FUNCTION fStaff
(@staff_id INT)
RETURNS VARCHAR(50)
AS
BEGIN
DECLARE @staff_name VARCHAR(50);
IF @staff_id < 10
SET @staff_name = 'Smith';
ELSE
SET @staff_name = 'Lawrence';
RETURN @staff_name;
END;
SELECT dbo.fStaff(8);
7
Example 2: BikeStores database
BikeStores
CREATE FUNCTION sales.fNetSale
(
@quantity INT,
@list_price DEC(10,2),
@discount DEC(4,2)
)
RETURNS DEC(10,2)
AS
BEGIN
RETURN @quantity * @list_price * (1 - @discount);
END;
SELECT order_id,
SUM(sales.fNetSale(quantity, list_price, discount)) net_amount
FROM sales.order_items
GROUP BY order_id
ORDER BY net_amount DESC;
9
Modifying a scalar function
10
Drop a scalar function
11
Some key points about scalar function
12
Table Variables in SQL Server
Table variables allow data records to be stored,
similar to the temporary tables
Declare a table variable:
DECLARE @table_variable_name TABLE
(
column_list
);
13
Table Variables in SQL Server (cont'd)
Example
14
Insert data into a table variable
DECLARE @product_table TABLE (
product_name VARCHAR(MAX) NOT NULL,
brand_id INT NOT NULL,
list_price DEC(11,2) NOT NULL
);
15
Limitations of table variables
The structure of a table variable must be
defined, and cannot be changed after it
has been declared, not like a regular table
or a temporary table.
Table variables don't contain statistics, so
it doesn't help the query optimizer to
come up with a good query execution
plan. Table variables should only be used
to store few records.
16
Limitations of table variables (cont'd)
17
Limitations of table variables (cont'd)
18
Performance of Table Variables in SQL Server
19
Using table variables in user-defined function
20
Using table variables in user-defined function
BEGIN
INSERT INTO @parts
VALUES (@string);
BREAK
END
IF (@index > 1)
BEGIN
INSERT INTO @parts
VALUES (LEFT(@string, @index - 1));
SET @string = RIGHT(@string, (LEN(@string) - @index));
END
ELSE
SET @string = RIGHT(@string, (LEN(@string) - @index));
END
RETURN
END
SELECT * FROM udfSplit('foo,bar,baz',',');
21
Table function in SQL Server
A table function is a user-defined
function that returns a table data type.
The return type of the table function is
a table, so the table function can be
used in the same way as the table.
22
Create and execute the table functions
CREATE FUNCTION udfProductInYear
(
@model_year INT
)
RETURNS TABLE SELECT *
AS FROM udfProductInYear(2017);
RETURN
SELECT SELECT product_name, list_price
product_name, FROM udfProductInYear(2018);
model_year,
list_price
FROM
production.products
WHERE
model_year = @model_year;
23
Modifying the table functions
ALTER FUNCTION udfProductInYear (
@start_year INT,
@end_year INT
) SELECT
RETURNS TABLE product_name,
AS model_year,
RETURN list_price
SELECT FROM
product_name, udfProductInYear(2017,2018)
model_year, ORDER BY
list_price product_name;
FROM
production.products
WHERE
model_year BETWEEN @start_year AND @end_year
24
Multi-statement table function
A function that has many statements and
returns a table value
Useful, because it is possible to execute multiple
queries within the function and aggregate the
results into the returned table
To define a table function, use a table variable
as the return value. Inside the function, execute
one/more insert queries into this table variable
25
Multi-statement table function
Example
CREATE FUNCTION udfContacts() INSERT INTO @contacts
RETURNS @contacts TABLE ( SELECT
first_name VARCHAR(50), first_name,
last_name VARCHAR(50), last_name,
email VARCHAR(255), email,
phone VARCHAR(25), phone,
contact_type VARCHAR(20) 'Customer'
) FROM sales.customers;
AS RETURN;
BEGIN END;
INSERT INTO @contacts
SELECT first_name, last_name,
email, phone, 'Staff'
FROM sales.staffs; SELECT *
FROM udfContacts();
26
When to use table functions?
27
Drop function
Syntax
DROP FUNCTION [IF EXISTS] [schema_name.] function_name;
28
Drop function (cont'd)
Remove multiple functions
DROP FUNCTION [IF EXISTS]
schema_name.function_name1,
schema_name.function_name2,
...;
29
Example
CREATE FUNCTION sales.udf_get_discount_amount
(
@quantity INT,
@list_price DEC(10,2),
@discount DEC(4,2)
)
RETURNS DEC(10,2)
AS
BEGIN
RETURN @quantity * @list_price * @discount
END
30
Delete function with WITH SCHEMABINDING
CREATE FUNCTION sales.udf_get_discount_amount
(
@quantity INT,
@list_price DEC(10,2),
@discount DEC(4,2)
)
RETURNS DEC(10,2)
WITH SCHEMABINDING
AS
BEGIN
RETURN @quantity * @list_price * @discount
END
31
CREATE VIEW sales.discounts
WITH SCHEMABINDING
AS
SELECT
order_id,
SUM(sales.udf_get_discount_amount(
quantity,
list_price,
discount
)) AS discount_amount
FROM
sales.order_items i
GROUP BY
order_id;
33
34