How to calculate a moving count?

JenniferMurphy

Well-known Member
Joined
Jul 23, 2011
Messages
2,687
Office Version
  1. 365
Platform
  1. Windows
As part of my moving sums and averages project described here:


I also need to calculate a moving count of cells containing numbers. My first try was with CountIfs, but I discovered here that CountIfs cannot be used with IsNumber and to use SumProduct:


I tried using SumProduct, as shown in the Count column in the minisheet below, but it isn't working. I can get what I want with two columns, IsNumber and Countx, but would prefer a single column. Is there a formula for the Count column that will get the result in the Countx column without needing the IsNumber column?

Moving Totals.xlsx
BCDEF
25Number of rows
3
4#ValueIsNumberCountxCount
515110
628120
73 020
842130
956140
106 030
1179130
1283140
139 030
14104130
Sheet2
Cell Formulas
RangeFormula
D5:D14D5=ISNUMBER([@Value])+0
E5:E14E5=SUM(TAKE(Table2[[#Headers],[IsNumber]]:[@IsNumber],-NumRows))
F5:F14F5=SUMPRODUCT(ISNUMBER(TAKE(Table2[[#Headers],[Value]]:[@Value],-NumRows)))
B5:B14B5=ROW([@['#]])-ROW(Table2[[#Headers],['#]])
Named Ranges
NameRefers ToCells
NumRows=Sheet2!$C$2E5:F14
 
You could do something like this to only count numbers:

Excel Formula:
=LET(mnum,MIN(NumRows,ROW()-ROW(Table1[#Headers])),mnum-COUNT(TAKE(Table1[[#Headers],[Time]]:[@Time],-mnum)))
 
Upvote 0

Excel Facts

How to find 2nd largest value in a column?
MAX finds the largest value. =LARGE(A:A,2) will find the second largest. =SMALL(A:A,3) will find the third smallest
You could do something like this to only count numbers:

Excel Formula:
=LET(mnum,MIN(NumRows,ROW()-ROW(Table1[#Headers])),mnum-COUNT(TAKE(Table1[[#Headers],[Time]]:[@Time],-mnum)))
I like it. ❤️ And it works! 😉 I wish I could mark more than 1 reply as a solution. 😢

I can't decide between this solution using Let and one using Offset. Any comments other than the volatility of Offset? To me the Offset solution is a little simpler.

Moving Totals.xlsx
CDEFGHIJ
5 5Number of rows
6DateTimeValueSumAverage#Rows#Missed (Let)#Missed (Offset)
71/01/242:51p222.00100
81/02/24 463.00211
91/03/2410:25a393.00311
101/04/245143.50422
111/05/248:15a1153.00522
121/06/2410:32a0132.60622
131/07/249:46a2112.20711
141/08/247153.00822
151/09/249:29a3132.60911
161/10/244:24p2142.801011
Sheet1
Cell Formulas
RangeFormula
F7:F16F7=SUM(TAKE(Table1[[#Headers],[Value]]:[@Value],-NumRows))
G7:G16G7=AVERAGE(TAKE(Table1[[#Headers],[Value]]:[@Value],-NumRows))
H7:H16H7=ROW()-ROW(Table1[[#Headers],['#Rows]])
I7:I16I7=LET(mnum, MIN(NumRows,ROW()-ROW(Table1[#Headers])), mnum-COUNT(TAKE(Table1[[#Headers],[Time]]:[@Time],-mnum)))
J7:J16J7=SUM(1-ISNUMBER(TAKE(OFFSET(Table1[[#Headers],[Time]],1,0):[@Time],-NumRows)))
Named Ranges
NameRefers ToCells
NumRows=Sheet1!$D$5I7:J16, F7:G16
 
Upvote 0
You might also have a look at mine using DROP…posted at the same time as Rory’s last.
 
Upvote 0
I see...maybe you do want ISNUMBER then, as you won't necessarily know whether apparent blanks are true blanks, or spaces, or something that you can't see. You could revert to the ISNUMBER formula, and because you have an official table, you'd like to exclude the first header row from consideration. An easy option to do that is to wrap the range selection in DROP, and then drop the first row...and then look back NumRows for the values to consider:
Excel Formula:
=SUM(--ISNUMBER(TAKE(DROP(Table2[[#Headers],[Value]]:[@Value],1),-NumRows)))
I thought I looked at this option and concluded that it would sometimes drop a non-header row. Now I see that it works. Thanks. Now I think I like this solution best.

And it handles random text as well. Thank you!🤩👍

Moving Totals.xlsx
CDEFGHIJK
5 3Number of rows
6DateTimeValueSumAverage#Rows#Blank (Drop)#Blank (Let)#Blank (Offset)
71/01/242:51p222.001000
81/02/24 463.002111
91/03/2410:25a393.003111
101/04/24xx 5124.004222
111/05/248:15a193.005111
121/06/2410:32a062.006111
131/07/249:46a231.007000
141/08/24793.008111
151/09/249:29a3124.009111
161/10/244:24p2124.0010111
Sheet1
Cell Formulas
RangeFormula
F7:F16F7=SUM(TAKE(Table1[[#Headers],[Value]]:[@Value],-NumRows))
G7:G16G7=AVERAGE(TAKE(Table1[[#Headers],[Value]]:[@Value],-NumRows))
H7:H16H7=ROW()-ROW(Table1[[#Headers],['#Rows]])
I7:I16I7=SUM(1-ISNUMBER(TAKE(DROP(Table1[[#Headers],[Time]]:[@Time],1),-NumRows)))
J7:J16J7=LET(mnum, MIN(NumRows,ROW()-ROW(Table1[#Headers])), mnum-COUNT(TAKE(Table1[[#Headers],[Time]]:[@Time],-mnum)))
K7:K16K7=SUM(1-ISNUMBER(TAKE(OFFSET(Table1[[#Headers],[Time]],1,0):[@Time],-NumRows)))
Named Ranges
NameRefers ToCells
NumRows=Sheet1!$D$5F7:G16, I7:K16
 
Upvote 0
thought I looked at this option and concluded that it would sometimes drop a non-header row.
The way the range is formed, it always begins with the header row down to your current row…and we drop only the first row, so that shouldn’t cause any problems.
 
Upvote 0
The way the range is formed, it always begins with the header row down to your current row…and we drop only the first row, so that shouldn’t cause any problems.
Yes, I see that now. I don't know now what I thought would go wrong.

Here is my more complete table comparing the three solutions. I added columns to show how many rows would be included in the tallies.

Moving Totals.xlsx
CDEFGHIJKLM
3 7Number of rows
4DateTimeValueSumAverage#Rows (Drop)#Rows (Let)#Rows (Offset)#Blank (Drop)#Blank (Let)#Blank (Offset)
51/01/242:51p222.00111000
61/02/24 463.00222111
71/03/2410:25a393.00333111
81/04/24xx 5143.50444222
91/05/248:15a1153.00555222
101/06/2410:32a0152.50666222
111/07/249:46a2172.43777222
121/08/247223.14777333
131/09/249:29a3213.00777222
141/10/244:24p2202.86777222
Sheet1
Cell Formulas
RangeFormula
F5:F14F5=SUM(TAKE(Table1[[#Headers],[Value]]:[@Value],-NumRows))
G5:G14G5=AVERAGE(TAKE(Table1[[#Headers],[Value]]:[@Value],-NumRows))
H5:H14H5=ROWS(TAKE(DROP(Table1[[#Headers],[Time]]:[@Time],1),-NumRows))
I5:I14I5=MIN(NumRows,ROW()-ROW(Table1[#Headers]))
J5:J14J5=ROWS(TAKE(OFFSET(Table1[[#Headers],[Time]],1,0):[@Time],-NumRows))
K5:K14K5=SUM(1-ISNUMBER(TAKE(DROP(Table1[[#Headers],[Time]]:[@Time],1),-NumRows)))
L5:L14L5=LET(mnum, MIN(NumRows,ROW()-ROW(Table1[#Headers])), mnum-COUNT(TAKE(Table1[[#Headers],[Time]]:[@Time],-mnum)))
M5:M14M5=SUM(1-ISNUMBER(TAKE(OFFSET(Table1[[#Headers],[Time]],1,0):[@Time],-NumRows)))
Named Ranges
NameRefers ToCells
NumRows=Sheet1!$D$3F5:M14
 
Upvote 0

Forum statistics

Threads
1,223,893
Messages
6,175,240
Members
452,621
Latest member
Laura_PinksBTHFT

We've detected that you are using an adblocker.

We have a great community of people providing Excel help here, but the hosting costs are enormous. You can help keep this site running by allowing ads on MrExcel.com.
Allow Ads at MrExcel

Which adblocker are you using?

Disable AdBlock

Follow these easy steps to disable AdBlock

1)Click on the icon in the browser’s toolbar.
2)Click on the icon in the browser’s toolbar.
2)Click on the "Pause on this site" option.
Go back

Disable AdBlock Plus

Follow these easy steps to disable AdBlock Plus

1)Click on the icon in the browser’s toolbar.
2)Click on the toggle to disable it for "mrexcel.com".
Go back

Disable uBlock Origin

Follow these easy steps to disable uBlock Origin

1)Click on the icon in the browser’s toolbar.
2)Click on the "Power" button.
3)Click on the "Refresh" button.
Go back

Disable uBlock

Follow these easy steps to disable uBlock

1)Click on the icon in the browser’s toolbar.
2)Click on the "Power" button.
3)Click on the "Refresh" button.
Go back
Back
Top