How to get uncommon elements in two lists in Excel? - excel

In excel i have two lists A and B of names. I want to get list C that contains uncommon elements in A and B.
How can i do this?

I figured this out by inverting the solution for finding common values given on this page:
How to find common values from two lists
It works as an array function, so you have to press ctrl + shift + enter after you enter it. The advantage of doing it as an array function is it doesn't leave a bunch of spaces to be edited out. All the relevant values are at the top.
I have a list of 40 reference values in Column A, I enter a list of 7 unknown values to compare in Column B, and I want to get a list in Column C showing the values in Column B that are NOT in Column A.
=INDEX($B$2:$B$7, SMALL(IF(COUNTIF($A$2:$A$40,$B$2:$B$7),"",ROW($B$2:$B$7)-MIN(ROW($B$2:$B$7))+1),ROW(B1)))
The COUNTIF statement generates an array of 1s and 0s, depending on whether the value in Column B is in Column A (1 if yes, 0 if no).
Since I'm looking for uncommon values, I have the IF statement return an array of row values corresponding to values in B that aren't in A. The ~Row-Min(Row)+1 bit makes sure you're using the right row value.
SMALL returns the ROW(B1)-smallest (like 1st smallest, or 4th smallest) from the array returned by the IF statement. So now I've got a single value instead of an array.
INDEX returns the value of the row in Column B.
Remember to press ctrl + shift + enter.

It's a little tricky but you can use the VLOOKUP function.
http://www.timeatlas.com/5_minute_tips/general/learning_vlookup_in_excel has a decent explanation for its use.

Related

Automation in Excel for shift patterns

Hi I have the following two tables
I am trying to get the col
I am trying to automate Column E so that every time the data changes in cell D2 it would automatically get changed based on the shift patter that the Agent is assigned on that day.
I cannot used vlookup because it will obviously just take the first text found with for example 9am-5pm - all cells would be populated with Agent 3.
=INDEX($A$2:$A$10,AGGREGATE(15,3,($B$2:$B$10=D3)/($B$2:$B$10=D3)*ROW($B$2:$B$10)-1,COUNTIF(D$3:D3,D3)))
As an alternate approach to ZygD's answer.
It uses AGGREGATE. It checks for the values in the B column range to equal the value in column D and divides the result by itself, which will result in 1 if True and multiplies that by the row number. The result gives the row numbers of all TRUEs and checks for the Nth smallest value based on how many of the same agent are already found in your result list above and finally shows the value of that row in your range of values in column A.
Seems like this array formula in E3 in part does what you want (it is entered not using usual Enter key, but instead, Ctrl + Shift + Enter).
=INDEX($A$2:$A$10,SMALL(IF(D3=$B$2:$B$10,ROW($B$2:$B$10)-ROW($B$2)+1),COUNTIF($D$3:D3,D3)))
Use XLOOKUP() instead. Column position does not matter with this function.

Find Length=2 cell in a given range

I have these two rows with an image path.
In Columns D-H i have only one cell that his length is 2.
I need to find it and do formulas based on it, and I would prefer not writing 5 times "IF", any quick way to find it?
It's unclear what you're asking but it seems like you're just trying to figure out which column has a string with a length of 2 characters.
If this is the case use this formula (assuming your data starts in row 2 of the columns you mentioned):
=match(2,len(D2:H2),0) However, when you write this hit CTRL + SHIFT + ENTER
Which will give you {=match(2,len(D2:H2),0)} this is an array formula you must carry down. This will give you the relative column of the string with 2 as its length. Relative meaning, if the criteria is met in column D, it will return 1 (instead of 4).
If you want the value, just use an Index match like so, using the same CTRL + SHIFT + ENTER I mentioned earlier.
{=index(D2:H2,match(2,len(D2:H2),0))}
Here's a non-vba, non-CTE/Array formula way to do this:
=SUMPRODUCT((LEN(D1:H1)=2)*COLUMN(D1:H1))
Will spit out the number of the column that has a length of 2. If more than one column fulfills this criteria then you will get back garbage. So don't do that.
You can pop that into Index() to get the value that was hit:
=INDEX(A1:H1, 1, SUMPRODUCT((LEN(D1:H1)=2)*COLUMN(D1:H1)))

Sum of Products if label is found in a list

I am trying to add together the products of all numbers whose labels appear in a list. For example, in the picture provided, we want the sum of the products of the numbers whose labels are a, e, c, or z. This would be 1*2+5*6+3*4=44.
I thought the formula in the picture would work because we would be taking the sum of the products of the first number and either the second number if the label is in the list, or zero otherwise, but I 'm not really sure why this doesn't work.
You need to enter the formula with Ctrl + Shift + Enter so the if countif is properly evaluated. That way you have two arrays of equal length for SUMPRODUCT.

Excel Column Missing Data

I have an excel spreadsheet that has a Name Date match in two columns for one list, and the same name date match for two columns in a 2nd list.
One list is longer than the other, how can I find the data that is missing in the matching date/name from the other list?
For instance let's say
List 1 List2
1/2/2012 Tim 1/2/2012 Tim
2/2/2012 Jill 2/2/2012 Jill
3/2/2012 Bob
So basically I need to search list one and find out that List 2 is missing "3/2/2012 Bob" both the dates and names are in their own columns.
How do I do this? Keeping in mind that these lists have no order and that it is possible that someone in list2 might show up in list1 just not on the same row.
If List 1 is in columns A and B, and List2 is in columns C and D, then select an area the same size as List 1 (or the size of List 1 minus List2--make sure it has 2 columns) and enter this as an array formula (ctrl+shift+enter):
=IFERROR(INDEX(A2:B4,SMALL(IFERROR(MATCH(A2:A4&B2:B4,C2:C3&D2:D3,0)+ROWS(A2:A4),ROW(INDIRECT("1:"&ROWS(A2:A4)))),ROW(INDIRECT("1:"&ROWS(A2:A4)))),{1,2}),"")
Expand the rows as needed. Also, you'll need to format the first output column as a date.
EXPLANATION UPDATE
The Evaluate Formula dialogue is helpful for breaking down complicated formulas. Select the cell with the formula and press alt then T then U then F ("TUF" for tough formulas...).
Start with the MATCH function. Since we're looking for a date-name match, concatenate the name and date columns with &. MATCH will tell us which pairs in List 1 are also in List2 (specifically where--we'll get an array of indices in List2 where the matches were found in List 1). If a match is not found, it will return #NA. So for the OP's example MATCH will return {1;2;#NA} (the first value in the List 1 array is in position 1 in List2, the second value is in position 2, and the third value was not found in List2).
The second argument in the inner IFERROR is an array of the indices of List 1. ROWS returns the number of rows in a range, INDIRECT returns a safe (meaning it won't be accidentally deleted or moved) reference to rows 1 through the number returned by ROWS, and ROW returns the row number of each of the rows--so in the OP's example, this is {1;2;3}.
We want the elements from List 1 that were not found in List2, so we add the number of rows in List 1 to the non-error MATCH results. This will send those values to the end of the array returned by SMALL. For the OP's example, the array passed as the first argument to SMALL is {4;5;3}.
Now we want to bring the indices of interest to the top using SMALL. We use ROW(INDIRECT("1:"&ROWS(A2:A4))) again as the second argument in SMALL to sort the array smallest to largest. For the OP's example, the resulting array is {3;4;5}.
We then pass that array to INDEX as the "row_num" argument and {1,2} as the column argument. INDEX will then pull both columns from the range that we give as its first argument for each row in the array that resulted from SMALL. The values at the end of the array that resulted from SMALL are larger than the number of rows in List 1 (since we added ROWS(A2:A4) to them), so they will result in #REF! errors. These correspond the the elements that returned a match in the MATCH function. We wrap this with yet another IFERROR to blank out the errors.

Sort Order formula to alphabetise in 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"

Resources