Logo

SQL Server RunningAVG Function

Updated 2023-11-14 13:44:51.573000

Description

Use the scalar function RunningAVG to calculate the average of column values in an ordered resultant table, without having to do a self-join. The average value is calculated for each value from the first value to the last value in the ordered group or partition. If the column values are presented to the functions out of order, an error message will be generated.

Syntax

SELECT [westclintech].[wct].[RunningAVG] (
  <@Val, float,>
 ,<@RowNum, int,>
 ,<@Id, tinyint,>)

Arguments

@Val

the value passed into the function. @Val is an expression of type float or of a type that can be implicitly converted to float.

@RowNum

the number of the row within the group for which the average is being calculated. If @RowNum for the current row in a set is less than or equal to the previous @RowNum and @RowNum is not equal to 1, an error message will be generated. @RowNum is an expression of type int or of a type that can be implicitly converted to int.

@Id

a unique identifier for the RunningAVG calculation. @Id allows you to specify multiple RunningAVG calculation s within a resultant table. @Id is an expression of type tinyint or of a type that can be implicitly converted to tinyint.

Return Type

float

Remarks

If @Id is NULL then @Id = 0.

To calculate moving averages, use the MovingAVG function.

To calculate moving averages for time series, use the DEMA or DWMA function.

If @RowNum is equal to 1, RunningAVG is equal to @Val.

@RowNum must be in ascending order.

There may be cases where the order in which the data are returned to the function and the order in which the results are returned are different, generally due to parallelism. You can use OPTION(MAXDOP 1) or OPTION(MAXDOP 1,FORCE ORDER) to help eliminate this problem.

Examples

In this example we will calculate the average check amount in a check register from the first check to the last check. We will create a temporary table, #c, populate it with some data and then run the SELECT.

/*Create the temporary table*/
CREATE TABLE #c
(
    num_check int,
    date_check datetime,
    payee varchar(50),
    amt_check money,
    Primary Key (num_check)
);
/*Populate the table with some data*/
INSERT INTO #c
VALUES
(1200, '2012-01-31', 'Gas Company', 108.49);
INSERT INTO #c
VALUES
(1201, '2012-01-31', 'Electric Company', 98.27);
INSERT INTO #c
VALUES
(1202, '2012-01-31', 'Telephone Company', 136.6);
INSERT INTO #c
VALUES
(1203, '2012-01-31', 'Car Leasing Company', 361.75);
INSERT INTO #c
VALUES
(1204, '2012-01-31', 'Mortgage Bank', 1129.23);
INSERT INTO #c
VALUES
(1205, '2012-02-29', 'Gas Company', 153.89);
INSERT INTO #c
VALUES
(1206, '2012-02-29', 'Electric Company', 121.99);
INSERT INTO #c
VALUES
(1207, '2012-02-29', 'Telephone Company', 138.92);
INSERT INTO #c
VALUES
(1208, '2012-02-29', 'Car Leasing Company', 361.75);
INSERT INTO #c
VALUES
(1209, '2012-02-29', 'Mortgage Bank', 1129.23);
INSERT INTO #c
VALUES
(1210, '2012-03-31', 'Gas Company', 70.79);
INSERT INTO #c
VALUES
(1211, '2012-03-31', 'Electric Company', 93.57);
INSERT INTO #c
VALUES
(1212, '2012-03-31', 'Telephone Company', 149.78);
INSERT INTO #c
VALUES
(1213, '2012-03-31', 'Car Leasing Company', 361.75);
INSERT INTO #c
VALUES
(1214, '2012-03-31', 'Mortgage Bank', 1129.23);
INSERT INTO #c
VALUES
(1215, '2012-04-30', 'Gas Company', 105.58);
INSERT INTO #c
VALUES
(1216, '2012-04-30', 'Electric Company', 149.36);
INSERT INTO #c
VALUES
(1217, '2012-04-30', 'Telephone Company', 145.35);
INSERT INTO #c
VALUES
(1218, '2012-04-30', 'Car Leasing Company', 361.75);
INSERT INTO #c
VALUES
(1219, '2012-04-30', 'Mortgage Bank', 1129.23);
INSERT INTO #c
VALUES
(1220, '2012-05-31', 'Gas Company', 96.27);
INSERT INTO #c
VALUES
(1221, '2012-05-31', 'Electric Company', 114.62);
INSERT INTO #c
VALUES
(1222, '2012-05-31', 'Telephone Company', 145.43);
INSERT INTO #c
VALUES
(1223, '2012-05-31', 'Car Leasing Company', 361.75);
INSERT INTO #c
VALUES
(1224, '2012-05-31', 'Mortgage Bank', 1129.23);
INSERT INTO #c
VALUES
(1225, '2012-06-30', 'Gas Company', 147.03);
INSERT INTO #c
VALUES
(1226, '2012-06-30', 'Electric Company', 130.52);
INSERT INTO #c
VALUES
(1227, '2012-06-30', 'Telephone Company', 147.71);
INSERT INTO #c
VALUES
(1228, '2012-06-30', 'Car Leasing Company', 361.75);
INSERT INTO #c
VALUES
(1229, '2012-06-30', 'Mortgage Bank', 1129.23);
/*Calculate the running average*/
SELECT num_check,
       cast(convert(varchar, date_check, 106) as char(11)) as date_check,
       cast(payee as char(20)) as payee,
       amt_check,
       wct.RunningAvg(amt_check, num_check, NULL) as [Running AVG]
FROM #c;

This produces the following result.

num_checkdate_checkpayeeamt_checkRunning AVG
120031 Jan 2012Gas Company108.49108.49
120131 Jan 2012Electric Company98.27103.38
120231 Jan 2012Telephone Company136.60114.453333333333
120331 Jan 2012Car Leasing Company361.75176.2775
120431 Jan 2012Mortgage Bank1129.23366.868
120529 Feb 2012Gas Company153.89331.371666666667
120629 Feb 2012Electric Company121.99301.46
120729 Feb 2012Telephone Company138.92281.1425
120829 Feb 2012Car Leasing Company361.75290.098888888889
120929 Feb 2012Mortgage Bank1129.23374.012
121031 Mar 2012Gas Company70.79346.446363636364
121131 Mar 2012Electric Company93.57325.373333333333
121231 Mar 2012Telephone Company149.78311.866153846154
121331 Mar 2012Car Leasing Company361.75315.429285714286
121431 Mar 2012Mortgage Bank1129.23369.682666666667
121530 Apr 2012Gas Company105.58353.17625
121630 Apr 2012Electric Company149.36341.187058823529
121730 Apr 2012Telephone Company145.35330.307222222222
121830 Apr 2012Car Leasing Company361.75331.962105263158
121930 Apr 2012Mortgage Bank1129.23371.8255
122031 May 2012Gas Company96.27358.70380952381
122131 May 2012Electric Company114.62347.609090909091
122231 May 2012Telephone Company145.43338.818695652174
122331 May 2012Car Leasing Company361.75339.774166666667
122431 May 2012Mortgage Bank1129.23371.3524
122530 Jun 2012Gas Company147.03362.724615384615
122630 Jun 2012Electric Company130.52354.124444444445
122730 Jun 2012Telephone Company147.71346.7525
122830 Jun 2012Car Leasing Company361.75347.269655172414
122930 Jun 2012Mortgage Bank1129.23373.335

In this example, we calculate the average by payee in date order and use the ROW_NUMBER() function to determine the @RowNum value passed into the RunningAVG function.

SELECT num_check,
       cast(convert(varchar, date_check, 106) as char(11)) as date_check,
       cast(payee as char(20)) as payee,
       amt_check,
       wct.RunningAvg(amt_check, ROW_NUMBER() OVER (PARTITION BY payee ORDER BY 
                 payee, num_check), NULL) as [Running AVG]
FROM #c
ORDER BY payee,
         num_check;

This produces the following result.

num_checkdate_checkpayeeamt_checkRunning AVG
120331 Jan 2012Car Leasing Company361.75361.75
120829 Feb 2012Car Leasing Company361.75361.75
121331 Mar 2012Car Leasing Company361.75361.75
121830 Apr 2012Car Leasing Company361.75361.75
122331 May 2012Car Leasing Company361.75361.75
122830 Jun 2012Car Leasing Company361.75361.75
120131 Jan 2012Electric Company98.2798.27
120629 Feb 2012Electric Company121.99110.13
121131 Mar 2012Electric Company93.57104.61
121630 Apr 2012Electric Company149.36115.7975
122131 May 2012Electric Company114.62115.562
122630 Jun 2012Electric Company130.52118.055
120031 Jan 2012Gas Company108.49108.49
120529 Feb 2012Gas Company153.89131.19
121031 Mar 2012Gas Company70.79111.056666666667
121530 Apr 2012Gas Company105.58109.6875
122031 May 2012Gas Company96.27107.004
122530 Jun 2012Gas Company147.03113.675
120431 Jan 2012Mortgage Bank1129.231129.23
120929 Feb 2012Mortgage Bank1129.231129.23
121431 Mar 2012Mortgage Bank1129.231129.23
121930 Apr 2012Mortgage Bank1129.231129.23
122431 May 2012Mortgage Bank1129.231129.23
122930 Jun 2012Mortgage Bank1129.231129.23
120231 Jan 2012Telephone Company136.60136.6
120729 Feb 2012Telephone Company138.92137.76
121231 Mar 2012Telephone Company149.78141.766666666667
121730 Apr 2012Telephone Company145.35142.6625
122231 May 2012Telephone Company145.43143.216
122730 Jun 2012Telephone Company147.71143.965

In this example we calculate 2 running averages which we will call the month-to-date (MTD) running average and the year-to-date (YTD) running average.

SELECT num_check as [check],
       cast(convert(varchar, date_check, 106) as char(11)) as date_check,
       cast(payee as char(20)) as payee,
       amt_check,
       ROUND(wct.RunningAvg(amt_check, ROW_NUMBER() OVER (PARTITION BY MONTH(
                 date_check)ORDER BY num_check), 1), 2) as [MTD AVG],
       ROUND(wct.RunningAvg(amt_check, num_check, NULL), 2) as [YTD AVG]
FROM #c
ORDER BY num_check;

This produces the following result.

checkdate_checkpayeeamt_checkMTD AVGYTD AVG
120031 Jan 2012Gas Company108.49108.49108.49
120131 Jan 2012Electric Company98.27103.38103.38
120231 Jan 2012Telephone Company136.60114.45114.45
120331 Jan 2012Car Leasing Company361.75176.28176.28
120431 Jan 2012Mortgage Bank1129.23366.87366.87
120529 Feb 2012Gas Company153.89153.89331.37
120629 Feb 2012Electric Company121.99137.94301.46
120729 Feb 2012Telephone Company138.92138.27281.14
120829 Feb 2012Car Leasing Company361.75194.14290.1
120929 Feb 2012Mortgage Bank1129.23381.1674.01
121031 Mar 2012Gas Company70.7970.79346.45
121131 Mar 2012Electric Company93.5782.18325.37
121231 Mar 2012Telephone Company149.78104.71311.87
121331 Mar 2012Car Leasing Company361.75168.97315.43
121431 Mar 2012Mortgage Bank1129.23361.02369.68
121530 Apr 2012Gas Company105.58105.58353.18
121630 Apr 2012Electric Company149.36127.47341.19
121730 Apr 2012Telephone Company145.35133.43330.31
121830 Apr 2012Car Leasing Company361.75190.51331.96
121930 Apr 2012Mortgage Bank1129.23378.25371.83
122031 May 2012Gas Company96.2796.27358.7
122131 May 2012Electric Company114.62105.44347.61
122231 May 2012Telephone Company145.43118.77338.82
122331 May 2012Car Leasing Company361.75179.52339.77
122431 May 2012Mortgage Bank1129.23369.46371.35
122530 Jun 2012Gas Company147.03147.03362.72
122630 Jun 2012Electric Company130.52138.78354.12
122730 Jun 2012Telephone Company147.71141.75346.75
122830 Jun 2012Car Leasing Company361.75196.75347.27
122930 Jun 2012Mortgage Bank1129.23383.25373.34