I'm trying to essentially do a Vlookup on two columns ID (where I want the match to be exact) and a date field (where I want it to be fuzzy).
Suppose you have a table in "Sheet1" about hospital admissions like so:
ID Admit_Date
000 01/01/2016
000 06/01/2016
001 02/01/2016
002 04/01/2016
Then I have another table in "Sheet2" about followup care like so:
ID Followup_Date
000 01/05/2016
000 06/06/2016
001 02/02/2016
002 04/04/2016
In sheet 1 I want to return the corresponding Followup_Date which is the closest Date After the Admit_Date
So my final result will look something like
ID Admit_Date Followup_Date
000 01/01/2016 01/05/2016
000 06/01/2016 06/06/2016
001 02/01/2016 02/02/2016
002 04/01/2016 04/04/2016
What's the best way to do this using a formula in Google Spreadsheets?
Update
Get " Followup_Date", formula on Sheet1
You could use this formula:
=QUERY(SORT(FILTER(sheet2!B:B,sheet2!A:A=A2,sheet2!B:B>=B2)),"limit 1")
Original (wrong) answer
Get "Admit_Date", formula on Sheet2
try this formula:
=VLOOKUP(B2,(FILTER(sheet1!B:B,sheet1!A:A=A2)),1)
you'll need to paste it in cell C2 and copy it down.
This formula is doing:
filtering data, doing exact match sheet1!A:A=A2
doind vlookup, with default parameter, that gives the closest Date After the Admit_Date. This will work with numbers, and date is serial number in spreadsheets, so this will fit you.
If you like big ArrayFormulas, here's one, that you don't need to drag down, it'll expand automatically:
=ArrayFormula(RIGHT(VLOOKUP(VLOOKUP(OFFSET(A1,1,,counta(A2:A)),{UNIQUE(FILTER(A2:A,A2:A<>"")),row(INDIRECT("A1:A"&COUNTUNIQUE(A2:A)))*100000},2,0)+OFFSET(B1,1,,counta(A2:A)),VLOOKUP(OFFSET(sheet1!A1,1,,counta(sheet1!A2:A)),{UNIQUE(FILTER(A2:A,A2:A<>"")),row(INDIRECT("A1:A"&COUNTUNIQUE(A2:A)))*100000},2,0)+OFFSET(sheet1!B1,1,,counta(sheet1!A2:A)),1),5)*1)
Related
I am trying to find a way to see which employees are not working between 2 dates.
Should I use vlookup, index & match, filter, query, or something else?
Sheet 1 contains employee details & start/end dates.
Sheet 2 accepts user input to select 2 dates, and it will automatically display a list of available employees who are not working.
Sheet 1 - Database/Log of all employees and days worked.
#
A
B
C
D
1
ID
Name
Start Date
End Date
2
12345
John
01/01/2021
01/08/2021
3
54321
Sarah
01/24/2021
01/29/2021
4
00731
James
02/05/2021
02/15/2021
5
00731
John
02/10/2021
02/30/2021
Sheet 2 (Row 1-2)- Manually enter in two dates.
#
A
B
1
Start Date (Manual input)
End Date (Manual input)
2
01/01/2021
01/30/2021
Sheet 2 (Row 3+)- List of all employees that are not working between the two dates entered in Sheet 2!A2:B2 (Expected Results)
#
A
B
3
ID
Name
4
00731
James
try:
=INDEX(SUBSTITUTE(UNIQUE(QUERY(""&SPLIT(FLATTEN(IF(SEQUENCE(1, MAX(D2:D-C2:C))<=D2:D-C2:C,
"♥"&A2:A&"♦"&B2:B&"♦"&C2:C+SEQUENCE(1, MAX(D2:D-C2:C), 0), )), "♦"),
"select Col1,Col2 where not Col3 matches '"&JOIN("|", "^$",
IF(SEQUENCE(1, G2-F2)<=G2-F2, F2+SEQUENCE(1, G2-F2, 0), ))&"'", 0)), "♥", ))
demo sheet
Assuming the name of your first sheet with the full data is actually Sheet1, place the following in Sheet2 cell A4:
=FILTER(Sheet1!A2:B,Sheet1!A2:A<>"",(Sheet1!C2:C>G2)+(Sheet1!D2:D<F2))
The combined either/or condition (Sheet1!C2:C>G2)+(Sheet1!D2:D<F2) in the FILTER means "either the start date is after the range date given, or the end date is before the range date given."
The other condition of Sheet1!A2:A<>"" just rules out blank rows in the original data set. It's not strictly necessary as far as the visual results are concerned; but it keeps null rows from being added to those results, which would allow you to enter data below the results in Col A and B of Sheet2 if you wanted, or to have fewer rows in Sheet2 than in Sheet1 without the formula adding more rows to accommodate null returns.
Your posted sample data is unclear. You have two different names for the same ID (i.e., 00731). And you have an "End Date" in D5 of February 30, 2021—which is not a valid date. In any case, it's unclear whether the same person/ID may turn up twice in the original data set. My formula above assumes you will not.
If your original data list may, in fact, contain duplicates, things get a bit trickier. In that case, use the following formula instead, in Sheet2 cell A4:
=UNIQUE(FILTER(A2:B,ISERROR(VLOOKUP(A2:A,FILTER(A2:A,((C2:C>=F2)*(C2:C<=G2))+((D2:D>=F2)*(D2:D<=G2))),1,FALSE))))
Here, the inner FILTER first forms a list of all people who are working during that range, and then the outer FILTER filters in a UNIQUE set of the people who are not on that inner list (i.e., trying to VLOOKUP them returns IS(an)ERROR).
So I am using a conditional formatting custom formula to highlight a cell if the column it is summing from another spreadsheet has blanks, but I don't know how to do it with changing ranges. Basically what I want to do is use a third column, say column A, to determine the length of the range (of rows) I want to scan with CountBlank, and if it picks up a blank in there to return a "True".
So basically:
Column A Column B Column C Column D
Person 1 5:30AM 3:00PM 9.5
Person 2 5:00AM 8
Person 3 4:30AM 4:00PM 10.5
So ideally, the cell sums the fourth column with a different function (already have that), and it conditionally formats itself if a blank is picked up in Columns B or C, going all the way down to the last row of column A that has a value. Any help here would be appreciated, thank you.
If I understand you correctly, the custom formula for conditional formatting should be:
=or(countifs(A2:A,"<>",B2:B,""),countifs(A2:A,"<>",C2:C,""))
Suppose you had a list of people's names starting in F2 and their total hours starting in G2. Then you could alter the formula to:
=or(countifs(A$2:A,F2,B$2:B,""),countifs(A$2:A,F2,C$2:C,""))
I'm struggling with the following and help/guidance would be appreciated. The attached Google Sheet has 3 sheets;
Sheet1 has 2 data fields (month, store name).
Sheet2 has 4 data fields (month, store name, fruit, quantity)
A query on Sheet3 in cell A3 outputs a set of months and store names from Sheet1 which is then used to find quantities of a given fruit from Sheet2 (in this example, it's apples). The results are listed on Sheet3 in columns D and E. I used both Index(Match) and Filter to output the Apple quantities as i tried to figure out my ultimate goal - how to use a single formula, including the query itself, to get to the aggregate apple total in Row 9 (i.e. without needing to do all the index(match) or filter formulas). Said another way, what formula on Sheet3 in cell D9 would run the query against Sheet1, use the results to find the month, store name, fruit, and quantity matches on Sheet2, and total them for a single output cell on Sheet3 D9?
Thoughts?
You can use a combination of counta(query()) to do this.
For A1:A that contains a mixture of fruit (apples, bananas, grapes, star fruit), use:
=counta((query(A1:A, "select A where A like 'apple'")))
Check out this very simple example sheet
Do you have a suggestion on how to make a formula for the problem written in the title?
Here is the example so that you can get an idea of the data format:
Name,Location,Category,Total views for your listing,Total uniqe page views for your listing,Average time on page (listing),total,Facebook,Reviews,Telephone,Treatment Menu,Get Directions,Book Appointment,Enquiry,Instagram,Date
John,NSW Sydney,Apple,1,1,0:00:12,0,0,0,0,0,0,0,0,0,13/Nov/2018
Mike,NSW Sydney,Orange,1,1,0:00:10,0,0,0,0,0,0,0,0,0,13/Nov/2018
Kenny,NSW Sydney,Pear,1,1,0:00:00,4,1,1,1,1,0,0,0,0,13/Nov/2018
John,NSW Sydney,Apple,20,1,0:00:12,0,0,0,0,0,0,0,0,0,14/Nov/2018
Chris,NSW Sydney,Orange,1,1,0:02:48,3,0,0,1,1,1,0,0,0,14/Nov/2018
Stef,NSW Sydney,Orange,10,1,0:07:22,6,1,1,0,1,0,1,1,1,14/Nov/2018
So, the issue is in making a formula that gets put into cells containing numerical values (from D to O), for each of the Name rows.
What it should look like is:
for John and for 13th and 14th of November, the cell in column B in that row should be 21
for Mike for 13th and 14th, it returns 1
for Jenny, which is not on the list, because she didn't have any values in any of the numerical columns for that day (or a group of days), it should return 0
All of these should appear in the "Main Dashboard" sheet, while the data is stored in the "directory statistics" sheet.
The predefined list of all the possible Names, Categories and Locations is in the "customList" sheet. This means that we don't need to search through the whole dataset of all the values for all the dates, but rather only search through the Names in the "customList". "Name" should be the key value that connects values in different dates.
So far, I have tried with this formula:
=Filter('directory statistics'!A2:A,'directory statistics'!$P2:$P=$P2)
It looks for the name column (A) and then returns the value if the date entered (in P2) matches the value in that sheet for the date column (P)
And then I got stuck! :)
Thank you!
I'm not sure why FILTER. Assuming Name in A1, and Row 1 and ColumnA in Main Dashboard set up as in my image, then:
=SUMIFS('directory statistics'!D$1:D$7,'directory statistics'!A$1:A$7,$A2,'directory statistics'!P$1:P$7,">="&B$1,'directory statistics'!P$1:P$7,"<="&C$1)
in B2 and copied down would appear to me to achieve the results you seek.
Let's say that we have two columns on a sheet:
Name Room
-------------
Steve A1
Jill A1
Sam A1
Steve A2
...
Lisa A10
Sally A11
Jim A11
My actual dataset has up to a hundred of these rooms.
The issue I'm running into is with pivot tables. When I want to get a list of rooms and the count (counta is the one I'm using) it works, but the order is not what I wanted. It comes out as:
Room Count
--------------
A1 3
A10 1
A11 2
...
A2 1
I guess I can kind of see why it would be doing that. I'd much rather have it list it out in order. A1, A2, A3... A10, A11, A12, etc.
Is there an easy way to do this without some sort of data manipulation?
An "easy" way to do this without "data manipulation" is to copy the PT, Paste special, Paste values only and then drag the relevant rows (presumably at most only 8) to where you want them. The easiest way is probably with "data manipulation", for example:
=if(len(A1)=2,SUBSTITUTE(A1,"A","A0"),A1)
(Though in you case, whichever column would be the right one, it would not be ColumnA.)
I suggest you transform the string elements into number values using a lookup table.
I've created a sample spreadsheet here.
The input data in the 'input' sheet has the keys as you described.
The next sheet is the "lookup table" to translate each key into a value number. I suggest choosing large numbers to leave room for future intermediate numbers if needed
Pivot 1 is based on the original data as you described
Pivot 2 is based on the re-calculated room name using the lookup table.
The formula I used for the re-calculation is:
=VALUE(SUBSTITUTE(A2,MID(A2,1,1),VLOOKUP(MID(A2,1,1),'Lookup table'!$A$1:$B$2,2)))
I was a little lazy with the string lookup in the original name (MID), assuming your string is the first character and is 1 character long. This can be mended specifically with pattern matching.