I need help with an Excel formula. I have to find the cell value based on a comma separated value list in another cell
For e.g Here G5 will have the max of Estimated End Date column (H) whose ID column contains values 1 or 2 (comma separated list in E5). Again above is e.g. there could be more than 2 values in the list
so G5 here should be 09/03/22 since it is max of 04/03/22 and 09/03/22.
We normally only respond to questions that include code or formulas we can work from (it's probably why you've received a downvote). However, in this case, I can see how you wouldn't know where to start.
Assuming you have Excel 365, the steps are:
Convert CSV to array
Map the array to found row numbers
Grab the max of the resultant array
I don't have the TEXT_SPLIT function, so I have to roll my own. I have a few helper functions for this (note these are saved as Names, in Formula->Define Name, so you'll need to add them).:
csvText
=LAMBDA(txt,"," & txt & ",")
csvCount
=LAMBDA(txt,LEN(txt)-LEN(SUBSTITUTE(txt,",",""))-1)
csvPosOf
=LAMBDA(n,txt,FIND("#",SUBSTITUTE(txt,",","#",n)))
csvLenOf
=LAMBDA(n,txt,csvPosOf(n+1,txt)-csvPosOf(n,txt)-1)
csvArray
=LAMBDA(txt,MAKEARRAY(1,csvCount(txt),LAMBDA(r,c,TRIM(MID(txt,csvPosOf(c,txt)+1,csvLenOf(c,txt))))))
This covers the splitting of your csv text to an array.
The mapping of the IDs to row numbers and MAX call is simply this formula:
=MAX(MAP(csvArray(csvText(C3)),LAMBDA(v,INDEX($A:$H,MATCH(VALUE(v),$A:$A,0),8))))
You'd add this formula into each row of your G column. Again, adjust the cell references as you need them. Please note you must call the VALUE function on the LAMBDA expression, as you can't implicitly MATCH a text representation of a number to an actual number.
Related
Let's say I have two strings in two cells
Cell A1 = Customer Country
Cell B1 = Customer City
I need to generate a unique ID using the Excel string functions (LEN, LEFT, MID, RIGHT etc.) or any other (CONCAT etc.) along with the ROW function.
Get first letter & last letter of each word, remove spaces and dashes, get the row number and return a unique string.
If I use
=IF(LEN(A$1)-LEN(SUBSTITUTE(A$1," ",""))=0,LEFT(A$1,1),IF(LEN(A$1)-LEN(SUBSTITUTE(A$1," ",""))=1,LEFT(A$1,1)&MID(A$1,FIND(" ",A$1)+1,1),LEFT(A$1,1)&MID(A$1,FIND(" ",A$1)+1,1)&MID(A$1,FIND(" ",A$1,FIND(" ",A$1)+1)+1,1))) &ROW(A$1)
I get results as CC1 in both cases. How would I get a unique ID in such as case.
The idea in the comment-section by #JosWoolley is a good one. Though, be careful how/where you'd add a column index. If you'd just add the column index number you'd create confusion between say CC111 from row 11 column 1 and the number from row 1 and possibly column 11. Just adding the actual address of the cell instead of these indices will help but can create confusion too if you don't add a delimiter first. Therefor I'd suggest something along the lines of:
Formula in D1:
=CONCAT(LEFT(TEXTSPLIT(A1," ")),"|",ADDRESS(ROW(A1),COLUMN(A1),4))
Note: If you don't yet have access to TEXTSPLIT() you can swap this with FILTERXML(). Also, you mentioned CONCAT() but if used with Excel 2019 you may need to CSE the formula.
I am currently trying to extract the prefix of a store ID to be able to then generate a list of stores with only that prefix.
Cell D1 has that formula to extract the unique prefix :
=TRANSPOSE(UNIQUE(LEFT(C2#, MIN(FIND({0,1,2,3,4,5,6,7,8,9},C2#&"0123456789"))-1)))
Cell C2 has that formula to extract the unique store ids from another sheet :
=UNIQUE(INDEX('Male Shoes'!A1#,,6))
The problem is that the formula in D1 only returns the first two characters from all the unique prefixes instead of using the correct value for each prefixes.
I have setup in column I the same formula as in D1 without the TRANSPOSE() and UNIQUE() functions and remove the # to see if that would return the correct value. I dragged it down the length of the C column.
=LEFT(C2, MIN(FIND({0,1,2,3,4,5,6,7,8,9},C2&"0123456789"))-1)
In Cell J2 I put the same formula has I2 but kept the # as a control.
=LEFT(C2#, MIN(FIND({0,1,2,3,4,5,6,7,8,9},C2#&"0123456789"))-1)
I believe the MIN() function is returning the minimum for the entire array and not for each row. I haven't found how to mitigated that problem anywhere online.
In my sample data that is not a problem since all the columns in D through G gave me the lists I was expecting but as more countries get added I might end up with duplicate country prefix. (i.e.: If the prefixes get shortened to 2 characters - Germany=GE and Georgia=GE)
If it is always 2 or three a simple IF instead of FIND will work:
=TRANSPOSE(UNIQUE(LEFT(C2#,IF(ISNUMBER(--MID(C2#,3,1)),2,3))))
Edit:
If there is only one time that it switches from alpha to numeric we can use:
=TRANSPOSE(UNIQUE(LEFT(C2#,MMULT(ISNUMBER(--MID(C2#,SEQUENCE(,MAX(LEN(C2#))),1))*ISERROR(--MID("A"&C2#,SEQUENCE(,MAX(LEN(C2#))),1)),SEQUENCE(MAX(LEN(C2#))))-1)))
This does not care how many characters are in the string, only that there is only 1 time that it switches from alpha to numeric. So ABDEFGHTEV4567 will work but A3D4 will not.
This is the problem i am facing in Excel formula
enter image description here
In column F, i want to find the common text across A2 to E2 (containing Blanks)
My Question:
Is there a simple way to get the result without VB?
Any help is appreciated,thanks
I found that google sheets has some really cool functions.
If you put the formula =SPLIT(A1, ",", TRUE,FALSE) in the cell after your row of common text (or probably even in a different sheet - "probably because hadn't tried it, though it should), the next x cells (where x is the number of "," in A1 - because "," is the delimitator) will be the text.
then you can put the code =IF(SUM(ARRAYFORMULA(if(REGEXMATCH($A$1:$D$1,F1),1,0)))=COUNTA($A$1:$D$1),F1,"") into an equal number of cells after that (probably should just put into the max number), and =CONCATENATE(I1:L1) into the last cell.
Ok. So to tweak this for yourself: I found that ARRAYFORMULA lets you put an array in place of a single cell in a function inside. how it exactly works I read its like a for loop. but I can't really vouch for that. but here it lets you have REGEXMATCH (which is a Boolean check on the cell you give it for if it contains the given REGEX) check each cell in the array.
the sum will add them up, and the if will match against the COUNTA to find if the number of cells in the array that contain this string is equal to the number of non-empty cells.
the concatenate at the end adds all the cells (containing the regex function) together, and since the only non-empty cells will be the one with the string, that is what this cell will return (no spaces).
code:
results:
the test data:
If you need in specifically Excel... this won't help.
We can use power query to achieve the desired result.
Unpivot the columns in Power query
Split all the columns by Comma delimiter
Create a custom column to see if the first column records exist in the remaining columns.
Use the functionText.contains.
Sample function: =Text.Contains([column.1],[column.1]&[column.2]&[column.3])
If the above function returns TRUE then get the first column result(This is the expected result) and load the data back to your excel
I am currently drawing up a spreadsheet that will automatically remove duplicates and alphabetize a list:
I am using the COUNTIF() function in column G to create a sort order and then VLOOKUP() to find the sort in column J.
The problem I am having is that I can't seem to get my SortOrder column to function properly. At the moment it creates an index for two number 1's meaning the cell highlighted in yellow is missed out and the last entry in the sorted list is null:
If anyone can find and rectify this mistake for me I'll be very grateful as it has been driving me insane all day! Many thanks.
I'll provide my usual method for doing an automatic pulling-in of raw data into a sorted, duplicate-removed list:
Assume raw data is in column A. In column B, use this formula to increase the counter each time the row shows a non-duplicate item in column A. Hardcord B2 to be "1", and use this formula in B3 and drag down.
=if(iserror(match(A3,$A$2:A2,0)),B2+1,B2)
This takes advantage of the fact that when we refer to this row counter in our revised list, we will use the match function, which only checks for the first matching number. Then say you want your new list of data on column D (usually I do this for display purposes, so either 'group-out' [hide] columns that form the formulas, or do this on another tab). You can avoid this step, but if you are already using helper columns I usually do each step in a different column - easier to document. In column C, starting in C3 [C2 hardcoded to 1] and drag down, just have a simple counter, which error-checks to the stop at the end of your list:
=if(C2<max(B:B),C2+1," ")
Then in column D, starting at D2 and dragged down:
=iferror(index(A:A,match(C2,B:B,0)),"")
The index function is like half of the vlookup function - it pulls the result out of a given array, when you provide it with a row number. The match function is like the other half of the vlookup function - it provides you with the row number where an item appears in a given array.
Hope this helps you in the future as well.
The actual reason that this is going wrong as implied by Jeeped's comment is that you can't meaningfully compare a string to a number unless you do a conversion because they are stored differently. So COUNTIF counts numbers and text separately.
20212 will give a count of 1 because it is the only (or lowest) number.
CS10Z002 will give a count of 1 because it is the first text string in alphabetical order.
Another approach is to add the count of numbers to the count if the current cell contains text:-
=COUNTIF(INDIRECT("$D$2:$D$"&$F$3),"<="&D2)+ISTEXT(D2)*COUNT(INDIRECT("$D$2:$D$"&$F$3))
It's easier to show the result of three different conversions with some test data:-
(0) No conversion - just use COUNTIF
=COUNTIF(D$2:D$7,"<="&D2)
"999"<"abc"<"def", 999<1000
(1) Count everything as text
=SUMPRODUCT(--(D$2:D$7&""<=D2&""))
"1000"<"999"
(2) Count numbers before text
=COUNTIF(D$2:D$7,"<="&D2)+ISTEXT(D2)*COUNT(D$2:D$7)
999<1000<"999"
(3) Count everything as text but convert numbers with leading zeroes
=SUMPRODUCT(--(TEXT(D$2:D$7,"000000")<=TEXT(D2,"000000")))
"000999" = "000999", "000999"<"001000"
I have variating numeric entries (SF123456, SF142365, ...). Every number of the numeric entries corresponds to a specific code. For each number of each entry I need to enter on a separate cell the corresponding code (download here example sheet: www.nivpat.com/Example.zip) How can I create an automatic function as I have thousands of entries to divide into codes... thanks!
Alright. What I did to solve this one is this:
Remove the '=' sign in your match table to be able to do a VLOOKUP on it;
Add the position of the digit you want to look up in the row 9 right above the headings. You might want to hide this row for cleaner presentation;
I used the following formula in the cells to extract the values:
=VLOOKUP(VALUE(MID($A11, B$9, 1)), $A$2:$B$7, 2, 0)
The VLOOKUP does the lookup on your table in A2:B7. The MID() extract exactly one character beginning with the character specified in B9 (in this case it would be 3). And the VALUE() converts the text string to a number to be able to do a match with the table above.
The only thing you now have to do is to drag your formulas and it's working !