Counting lowest values from multiple columns - excel

I have a table and I need to count expiration for a year but I have two columns and I need to count the lowest value from them. What function would help with this. Here is a small Example
Name Expiration date Break date
Nr.1 31-Aug-2019 28-Feb-2023
Nr 2 18-Oct-2018
Nr 3 30-Sep-2018 21-Jun-2017
Nr. 4 1-Jan-2018
AS you can see there will be here:
2017 2018 2019 2020
1 2 1 0

You could use an extra "helper" column which takes the minimum between the expiration date and break date. (Accounting for the possibility of the Break date being empty)
Then your equation to find the totals for each year would just be a simple COUNTIF on that new column.

Slightly shorter version of a formula for the helper column:
=YEAR(IF(COUNT(B2:C2)=2,MIN(B2:C2),B2+C2))
with the difference that this will return a year (other than 1900) if there is a blank in the Expiration date column that is next to a populated cell in the Break date column.
For the actual counts I would choose a technique that has been deemed off topic for SO.

Solution with no helper column
Formula:
=SUMPRODUCT(--((($B:$B<$C:$C)+($C:$C=""))*($B:$B<>"")*(YEAR($B:$B)=E$1))+((($C:$C<$B:$B)+($B:$B=""))*($C:$C<>"")*(YEAR($C:$C)=E$1)))
Assumptions:
Data in columns A:C, with Expiration Date in B and Break Date in C
Year (2017,2018,2019,2010) in E1:H1
The formula can be dragged horizontally from E2 to H2.
Formula Logic (pseudo-code):
IF(OR(AND(OR(B<C,C=""),B<>"",YEAR(B)=X),AND(OR(C<B,B=""),C<>"",YEAR(C)=X))) THEN TRUE
Alternate Solution Using Table
Because the headers break the original formula, you'll need to make the column references more specific to where the data actually is. A table is the easiest way to do that.
=SUMPRODUCT(--(((Table1[Expiration Date]<Table1[Break Date])+(Table1[Break Date]=""))*(Table1[Expiration Date]<>"")*(YEAR(Table1[Expiration Date])=$E1))+(((Table1[Break Date]<Table1[Expiration Date])+(Table1[Expiration Date]=""))*(Table1[Break Date]<>"")*(YEAR(Table1[Break Date])=$E1)))
Tables don't play nice with formulas dragged horizontally, so I put the years in a column:

=SUM(IF(YEAR(IF($B$2:$B$5
Note: This is an array formula, you must paste it in the cell, then hit ctrl+shift+enter and then you can copy and paste it across your table.
The cell works if your data is in A1:C5 and you have the years you want to test across E1:H10. You could then paste the above formula in E2, and then paste accross your table.
The array formula does the following:
The first IF statement checks to see which value is lower, ColB or ColC.
The embedded IF statements then check to make sure the values are not 0. If they are 0 they return the other column, if they are not 0, they return its own non-0 value.
The YEAR function extracts the year from each date.
The last IF function preformed (but the first written in the function) tests the year against the cell above the sum. If the year matches, it returns 1, if false, 0
The SUM statement simply sums all the true values

Related

Find an intersecting value for each row and column in excel

I have monthly data in rows in column A. I also have monthly data in headers from column B to Column G. In Column H i have current month populated for all rows. I would like to display the value where, for example if the month in row is Jan and current month is Mar, then find the value where Jan and Mar intersect and do this for all rows. I tried using the following formula in Column J but it only gives the first value when it works. The result in Column I is desired. Attached is the picture for clarity.
=INDEX(B1:H2,MATCH(A2,$A$1:A2,0),MATCH(A2,$B$1:H2,0))
You can do it with SUMPRODUCT.
I made a fake dataset with different values than the ones you show, so i could test properly if changing Current month would work.
It works even if column CurrentMonth holds different months
My formula is:
=SUMPRODUCT(--($B$1:$G$1=H2);B2:G2)
This is how it works:
--($B$1:$G$1=H2) will return an array of 1 and 0 if range B1:G1 is equal to current month in that row. So in case CurrentMonth=Mar then it will return {0;0;1;0;0;0}
With SUMPRODUCT we multiply previous array by range B:G in current row, so for row 2, it would be B2:G2. So as example, it would be {0;0;1;0;0;0} * {1;2;3;4;5;6} = {0;0;3;0;0;0} and we sum up this array, getting 3
just use INDEX with one MATCH:
=INDEX(B2:G2,,MATCH(H2,$B$1:$G$1,0))

In Excel how to count between date1 and date2 that have cells in row that contain text?

I need to choose cells in one column that are between two dates, and then based on the rows that contain those dates, choose cells in another row that also contains content.
I didn't use ISBLANK because it counts a formula yet an empty cell as a not-blank. Instead check if there is content by "*".
Here is what I came up with, but instead of returning the number of cells, instead this returns TRUE (which obviously isn't what I want).
In the formula below I am assuming:
C:C is the whole column containing DATES.
E:E is the whole column containing CONTENT.
The date range in this case is January 1, 2018 to January 31, 2018.
"*" means is there is content in the cell
=IF(AND(COUNTIFS(C:C,">="&"2018-1-1",C:C,"<="&"2018-1-31"),COUNTIF(E:E,"*"))=0,"",AND(COUNTIFS(C:C,">="&"2018-1-1",C:C,"<="&"2018-1-31"),COUNTIF(E:E,"*")))
My goal is to:
count the numbers of the cells in column E that are between the dates in column C
if the whole formula is 0, then return a blank.
See this picture of a sample excel sheet to make my intent clear:
How can I get my formula working so it does as needed?
SOLUTION
Hi all, so thanks to #girlvsdata, we have a working solution. I had to do a couple edits to her code to work for my uses, but her formula overall works perfect. Here is the solution:
To choose all cells in column E that are not blank, in between the date range of all of January (unknown end date) based on the adjacent C column if that is your date column, then the solution is:
=IF(COUNTIFS(C:C,">="&"2018-1-1",C:C,"<="&EOMONTH("2018-1-1",0),E:E,"*")=0,"",COUNTIFS(C:C,">="&"2018-1-1",C:C,"<="&EOMONTH("2018-1-1",0),E:E,"*"))
Note that "2018-1-1" is January 1 2018, and EOMONTH("2018-1-1",0) is the last valid day of January in the year 2018 (in this case, 31, but if it is different another year (e.g. for February this works for leap years too) then it will be that last day). Also it eliminates the need to calculate which is the last day or every month, as well as months that have changing end dates dependent on the year (e.g. Feb). This is important to eliminate a margin of error.
The only thing you have to do to change the month is only change e.g. -1- (Jan) to -2- for Feb, or change the year for other years. With this formula you can ignore the day part.
If the answer is 0 (no cells have any content in between the range), then the cell is blank instead of 0. (GOod for when you want to create a sheet checking future dates for future reference when more rows are added to the sheet.
It also works across different sheets, just use, say your other sheet is called "Tracker" then use Tracker!C:C and Tracker!E:E. Hope it helps!
Thank you all! :D
(Please note: My local date format is day, then month)
With the data laid out as in your example above:
A B
1 Dates |Content
------------+-------
2 1/01/2018 |
3 2/01/2018 |123456
4 3/01/2018 |
5 4/01/2018 |12398
6 5/01/2018 |484
7 6/01/2018 |1538
8 7/01/2018 |
9 8/01/2018 |
10 9/01/2018 |
11 10/01/2018 |14648
12 11/01/2018 |
13 12/01/2018 |145615
14 13/01/2018 |
And with the date range in cells D2 and E2:
Date Start Date End
2/01/2018 7/01/2018
This formula returns the count:
=COUNTIFS(A:A,">="&D2,A:A,"<="&E2,B:B,">0")
This will depend on whether your numbers in Column B are formatted as text or number. If they are formatted as numbers, the above formula will work. If they are formatted as text, replace the last section ">0" with "*".
This formula adds the conditional part of your question:
=IF(COUNTIFS(A:A,">="&D2,A:A,"<="&E2,B:B,">0")=0,"",COUNTIFS(A:A,">="&D2,A:A,"<="&E2,B:B,">0"))
(If the formula returns 0, show blank)

Dynamic starting point of OFFSET and SUM formula

I have the following Excel spreadsheet:
A B C D E F G
1 Year 2015 2016 2017 2018 2019 2020
2 Revenue 5.000 4.000 6.000
3 Years to go back: 2
4 Sum of Periods: 10.000
In Row 1 you can find the years 2015 til 2020 and in Row 2 the corresponding revenue of each year.
In Cell C3 the user should input the number of years to go back and sum up the revenues. For example if the user puts in a 2 Excel goes back 2 years and sums up the revenue of 2017 and 2016 which is 10.000 in the case above. For this I used the following formula:
=SUM(OFFSET($E$2,0,-C3):$E$2)
This formula and the described calculation above work perfectly so far.
However, in 2018 I will have to adjust the starting point of Cell $E$2 in the formula above to Cell $F$2. Ohterwise the year 2018 will be excluded from the calculation.
=SUM(OFFSET($F$2,0,-C3):$F$2)
My question is now how can I avoid this permanent re-adjustment every year?
--> I think the solution should be a formula that identifies the first "non empty" cell within in a Row and then starts counting back the years from this cell. Somehow a combination of the SUM, OFFSET, ROW & COLUMN formula.
You may use this formula:
=SUM(INDIRECT("R2C" & (MATCH(YEAR(TODAY()),$1:$1,0) - $C$3 + 1) & ":R2C" & MATCH(YEAR(TODAY()),$1:$1,0), FALSE))
But be aware I'm assume the current year - $C$3 is within your data range.
Brief explain:
YEAR(TODAY()) - it will return the year of current date, then you don't need to re-adjust every year
MATCH(lookup_value, lookup_array, match_type) - it will find the value matched in first row, and return the index of cell
INDIRECT() - Form the result of match to a R1C1 notation, and convert the text to excel range
A simpler formula could be to use the 4th parameter of OFFSET to set the width and to calculate the starting point of the OFFSET using YEAR(TODAY()0-2016
=SUM(OFFSET($B$2,0,YEAR(TODAY())-$C$1,1,$B$3))
NON VOLATILE OPTION
Well non volatile if it were not for the TODAY() function. Replace TODAY() with a cell containing the starting year as a date. or replace Year(Today()) with a cell reference just containing the year (integer) and then it will be a non volatile option.
=SUM(INDEX($1:$1,MATCH(YEAR(TODAY()),$1:$1,0)):INDEX($1:$1,MATCH(YEAR(TODAY()),$1:$1,0)-($C$3-1))
Volatile functions recalculate every time something on the spreadsheet changes.
Non volatile functions only recalculate when something affecting them changes.
The index function returns the cell address with in the range its looking. for a 2D range you need to give row and column reference. For a 1D range, you only need to give find the position within the range.
Match finds a value within a given range.

Excel - how to get if a date is a specific day of the week?

I have a spreadsheet that tracks average file processing times over the course of a month. One of the macros and stats that we like to pull, is performance on Mondays (as the files are a little built up over the weekend). The spreadsheet is organized into columns by weekdays of the month:
The dates are formatted MM/DD/YYYY, so I would think Excel has a date function that it can determine weekday based on that date value.
Currently, I just have to manually tell the Macro which columns are Mondays, like so:
=AVERAGE(B20,G20,L20,Q20)
So, instead of manually, how would I get the average over the range of say, B20 to V20, only if the day of the week is Monday (the date cells are in row 1, so B1 to V1)?
To determine the weekday of a date in EXCEL use the =WEEKDAY() formula, which evaluates as 1 (Sunday) to 7 (Saturday)
e.g. If A1 contains 12/31/2016 (or 31/12/2016 if you're from where I'm from), the formual =WEEKDAY(A1) would evaluate to 7 (indicating that the last day of 2016 was a Saturday)
To apply this formula to your problem: (assuming that the dates are in row 1 and the values are in row 2)
insert a new row to hold the WEEKDAY() value (say, row 2)
in cell A2 type in =WEEKDAY(A1)
copy this formula as far right as necessary (to include all your dates)
Your average for Mondays is calculated as =AVERAGEIF(2:2, 2, 3:3)
Possibly, you can add a column called [Day Of The Week] and use the following formula to display the day.
TEXT(B4,"dddd")
Then add an 'If'statement to your result cell.
simply
=SUMPRODUCT((MOD(B1:V1,7)=2)*B20:V20)/SUMPRODUCT((MOD(B1:V1,7)=2)*1)
should give the average of all values from B20 to V20 if the corresponding cell in row 1 is a monday.
the first part sums the values of all mondays and the second part counts them (sum / count = average) ;)
If you have any questions, just ask.
If your date is in A1, you can use =Text(A1,"dddd") to determine the day of the week (it will return the name, "Monday", "Tuesday", etc.) so then you could do perhaps:
=If(text(A1,"dddd")="Monday",[do whatever],[do whatever]) (may need a helper row/column to hold the text of the weekday)
(Or use AverageIf() and use the Text() idea.)

Index/Match Multiple Criteria, Perform Calculation for Each Match

I have two columns in a table that are known as S and D, where S is a date, and D is a duration.
E.g.:
'S' Column
January
February
March
April
'D' Column
60
30
45
30
On a separate sheet, imagine that Row 1 contains a sequence of dates (variable, depends on user menu selection).
Row 2 requires the following calculation:
[(x - s1)/d1 + (x-s2)/d2 + ... + (x-sn)/dn] / n
...where "x" is any date along Row 1.
The calculation would only be done when multiple criteria are matched.
My initial attempt involved creating a separate table, but I think this can be done in a one-cell formula in Row 2. I don't think a sum(index(match)) type would work here considering d1, d2, ..., dn are denominators with different values.
Here is an example attempt:
=SUM((SelectedDate-INDEX(Table[StartDates],MATCH(Criteria1&Criteria2,Range1&Range2,0))/INDEX(Table[Durations],MATCH(Criteria1&Criteria2,Range1&Range2,0))))
It may be important to note that I am able to do this in a two-step fashion. First, I create a table that does the calculation on each row. Then, I reference the table. It would be nice if I can eliminate the need of a "calculation table" in favour of an array-type formula.
I took a guess before most of the comments and suggest the following mainly in case it provides ay ideas or is of help in specifying the requirement more closely. This is "two-step" because the average formula is separate from that for each column, so I appreciate may well be not what is required.
Assuming S and D are labelled data in Sheet2 ColumnsA:B.
Assuming Row1 data rows are labelled in ColumnA.
Assuming dates are not strings (eg January is actually Jan 1) and the differences are in days and always positive, etc.
=(B$1-CHOOSE(COLUMN(),Sheet2!$A1,Sheet2!$A2,Sheet2!$A3,Sheet2!$A4))/CHOOSE(COLUMN(),Sheet2!$B1,Sheet2!$B2,Sheet2!$B3,Sheet2!$B4)
in Row2 to suit and if four data columns, in F2 and copied down to suit :
=AVERAGE(B2:E2)

Resources