Excel Lookup Return Unique Value - excel

I have two sheets one has
Item ID
Box 78
Glue 105
Box 85
The other sheet
Item ID
Box
Box
Glue
On the second sheet I want to look up the an ID from the first sheet.
Where there I duplicates (as in Box) I want to return the IDs one at a time.
So the lookup on Box would return 78 the first time, and 85 the second time.
Like this:
Item ID
Box 78
Box 85
Glue 105

Alternate solution. Does not require helper columns, does not require array entry. In Sheet2 cell B2 and copy down:
=INDEX(Sheet1!$B$2:$B$4,MATCH(1,INDEX((Sheet1!$A$2:$A$4=A2)*(COUNTIF(B$1:B1,Sheet1!$B$2:$B$4)=0),),0))

You can use a slight variation of INDEX/MATCH:
=INDEX(B$2:B$4,SMALL(IF(A$2:A$4=C2,ROW(B$2:B$4)-1,""),COUNTIF(C$2:C2,C2)))
Confirm as an array formula with Ctrl+Shift+Enter, then autofill down.
Explanation of cell references:
A$2:A$4 - Item Column (sheet1)
B$2:B$4 - ID Column (sheet1)
C$2:C2 - Item Column (sheet2)
C2 - The item you're looking up

At first glance this seems impossible, because VLOOKUP doesn't know how to deal with multiple Boxes.
But using this ingenious answer you actually CAN make this work.
On Sheet 1, enter the formulae:
Which results in:
item instance combined id range_above
Box 1 Box1 78 $A$2:$A$2
Glue 1 Glue1 105 $A$2:$A$3
Box 2 Box2 85 $A$2:$A$4
You can now VLOOKUP off combined instead of off item. (Obviously you'll have to do an identical trick in sheet 2.)
Note this all these formulae can just be extended down however long your table is. It will always just work.

A good method for doing this would be to use an array formula to look up the values from the first sheet using the number of repetitions of each item from the second sheet. This method requires no "helper" columns.
The formula that will accomplish this is: {=INDEX(Sheet1!A:B,SMALL(IF((Sheet1!A:A)=Sheet2!A2,ROW(Sheet1!A:A),""),COUNTIF($A$2:$A2,"="&$A2)),2)}
This formula is an array formula. You can copy it into cell B2 on Sheet2, and press Ctrl+Shift+Enter to enter it. You must press Ctrl+Shift+Enter to make this an array formula. You can drag this formula down column B for as many rows as you would like.
Your worksheet, when finished, will contain the following formulas:
Let's break this formula down into its components:
Identify how many times a given item has been repeated in column A. We accomplish this with the following code, which will count the number of times that the current row's item has appeared in all previous rows in column A. The absolute reference for the start of the range and the relative reference for the end ensures that the range will be automatically updated as we drag the formula down in column B:
COUNTIF($A$2:$A2,"="&$A2)
Identify the kth row in Sheet1 containing the item in column A of Sheet2. The following code first uses an IF statement to find all rows in Sheet1 containing the item in Column A of Sheet2. This uses array syntax to compare all rows in the specified range against a value. The IF statement returns an array containing the rows that were identified if any were found. If none were found, it returns the empty string.
IF((Sheet1!A:A)=Sheet2!A2,ROW(Sheet1!A:A),"")
Look up the value of the nth row that was identified using the SMALL function, which selects the nth smallest item from an array. For k, we pass the count that was calculated in step 1.
SMALL(IF((Sheet1!A:A)=Sheet2!A2,ROW(Sheet1!A:A),""),COUNTIF($A$2:$A2,"="&$A2))
Finally, we put it all together in the INDEX function, which will look up the value at the specified row (identified in step 3) and column (2), in a given range.
{=INDEX(Sheet1!A:B,SMALL(IF((Sheet1!A:A)=Sheet2!A2,ROW(Sheet1!A:A),""),COUNTIF($A$2:$A2,"="&$A2)),2)}

Related

Check if text exist in rest of Column, and if so, use info from that row it is in

I'm after a way to a cell to check another cell that I'm inputting text into, and for it to see if that text value is the same anywhere else in the column, and if so, it grabs the number value which is in the same column as itself but in the row of the text that checked for.
So if you use picture, you can see I've currently got E7 selected. I'm wanting it to check the "GOLF COURSE" column for any other row that contains the same text it has in it's own row. For this it's "Course1". I'd like it to check through the rest of column B if there are any matches for "Course1" which there is in B3. If it matches I'm wanting it to then use the value that's in same column as it (E) but the same row as the matched text in column B. In this case I would want it to copy the value that is in E3.
If there wasn't a match (as it's a new course lets say) then I need to be able to just click on the cell and input the numbers needed, which I would be able to do anyway but just throwing it in for sake of info.
I've tried all sorts of googling and thinking how I could possibly do it but it's too difficult for my amateur knowledge of Excel.
I believe you are looking for INDEX/MATCH:
=IF(COUNTIF($B:$B,$B7)>1,INDEX(E:E,MATCH($B7,$B:$B,0)),"New")
I added a COUNTIF check to ensure that the same course exists more than once in column B, without it, you would be getting a circular reference formula (which would also happen with the above formula if the same course appears more than once, but you use this formula on the first occurrence of that course, so make sure do not use it the first time you fill out the PAR scores for a particular course).
Merged Cells Messing With INDEX/MATCH
The Formula
Copy the following formula into cell E7:
=IF(AND($B7<>"",$D7="Par"),IF(ISERROR(MATCH($B7,$B$3:$B5,0)),"Par",INDEX(E$3:E5,MATCH($B7,$B$3:$B5,0))),IF(AND($B6<>"",$D7="Strokes"),IF(ISERROR(MATCH($B6,$B$3:$B4,0)),"Strokes",INDEX(E$3:E4,MATCH($B6,$B$3:$B4,0)+1)),""))
Image
How
We are creating the formula in cell E7.
MATCH
Syntax: MATCH(lookup_value,lookup_array,match_type)
We will use MATCH to find the position of COURSE1 in the above
cells of column B.
The 1st argument is lookup_value which will be the cell in the same
row of our row (7) in column B: B7 where we will lock only the
column (we will not be searching in other columns): $B7.
The 2nd argument lookup_array will be a range. The first cell will be
cell B3 whose row and column we'll lock, because we will always
start the search from this cell in every other cell to the left or
below: $B$3. The last cell will be B5 where we will lock only the
column: $B5.
And finally we will use 0 as the parameter of the 3rd argument
match_type to find an exact match.
Now were ready to write our MATCH formula:
=MATCH($B7,$B$3:$B5,0)
Which will return 1 i.e. an exact (0) match of B7 was found
in the 1st cell of range B3:B5.
We don't want 1 (E3), but the value in the cell (5).
INDEX
The INDEX function has 2 syntaxes where we will use the 2nd:
Syntax 2: INDEX(reference,row_num,column_num,area_num)
Since were using a one-column range we can safely omit the arguments row_num and column_num, which leaves us with:
Modified Syntax: INDEX(reference,area_num)
The INDEX function used this way will return the area_num-th value
of reference i.e. in our case if area_num is 1 it will return the
1st value in our column range, if it is 2, then the 2nd, etc.
The 1st argument reference will be the same sized range of our
MATCH range in column E: $E$3:$E5 where we will remove the
column locks because we also want to return results for other
columns: E$3:E5.
The 2nd argument area_num will be our MATCH formula.
Our current formula looks like this:
=INDEX(E$3:E5,MATCH($B7,$B$3:$B5,0))
which will return the value of cell E3: 5.
Final Adjustments: IF, AND and ISERROR
That would have been almost (Error Checking) all if the cells in column B weren't merged. Therefore we have to use IF to determine if the row in which we're writing the formula contains either Par or Strokes and adjust our so far created formula for both conditions:
=IF($D7="Par",INDEX(E$3:E5,MATCH($B7,$B$3:$B5,0))
=IF($D7="Strokes",INDEX(E$3:E4,MATCH($B6,$B$3:$B4,0)+1)
=IF($D7="Par",INDEX(E$3:E5,MATCH($B7,$B$3:$B5,0)),$D7="Strokes",INDEX(E$3:E4,MATCH($B6,$B$3:$B4,0)+1))
and (3rd condition) check in column B if there is a value in the row where we're creating the formula for a row containing Par, or the row above for a row containing Strokes, using AND:
=IF(AND($B7<>"",$D7="Par"),INDEX(E$3:E5,MATCH($B7,$B$3:$B5,0)),IF(AND($B6<>"",$D7="Strokes"),INDEX(E$3:E4,MATCH($B6,$B$3:$B4,0)+1),""))
Finally we have to add some error checking, because if the match was not found the formula will produce and #N/A error:
=IF(AND($B7<>"",$D7="Par"),IF(ISERROR(MATCH($B7,$B$3:$B5,0)),"Par",INDEX(E$3:E5,MATCH($B7,$B$3:$B5,0))),IF(AND($B6<>"",$D7="Strokes"),IF(ISERROR(MATCH($B6,$B$3:$B4,0)),"Strokes",INDEX(E$3:E4,MATCH($B6,$B$3:$B4,0)+1)),""))
Now we are ready to copy the formula to the right and below as far as we need.

Excel: An array in an array?

So, I would like to return the contents of all rows where the value in column A is, let's say, 1.
My thought process is that I could use:
=INDEX(row_range,MATCH(1,A:A,0),0))
But Match will only return one value here, i.e. the number of the first row which contains a 1 in column A.
Is there a way of creating an array with the Match formula (thus returning the multiple row numbers, all of which contain '1' in column A) and then place that in the Index array so that it then runs through each of the Match-array values and creates a big long list of values in one array which I can then list out on a separate sheet?
Hope this makes sense...
Here is a demonstration of what I'm hoping for, if that helps! The idea would be that the array as shown would be created, which could then be extended down the column as per the part underneath.
https://i.stack.imgur.com/nCusM.png
Use the file you showed in your example (as "Sheet1") and put these formulas into indicated cells in Sheet2:
Into cell A2 put
=AGGREGATE(15;6;ROW(Sheet1!A:A)/((Sheet1!A:A=1)*1);ROW(A1))
this will give you all the rownumbers where value in A column of sheet1 equals 1.
Into cell B2 put
=COUNTA(INDIRECT("Sheet1!"&A2&":"&A2))-1
this will give you how many cells are filled in that row.
Into cell C2 put
=TEXTJOIN(",";TRUE;OFFSET(Sheet1!$A$1;A2-1;1;1;B2))
This will give you all the cells with data from that row concatenated. If you dont have this formula (first time in 2016 I believe) you can use OFFSET function to list the values in separate columns and then CONCATENATE them.
Copy these three down as many times as you want and into cell C1 put
=TEXTJOIN(",";TRUE;OFFSET(C2;0;0;COUNTIF(Sheet1!A:A;1);1))

IF Function/VLOOKUP Combo

So this seems like it should be pretty easy. I could just concatenate and make another column in the data to make a unique combo and get my answer. But that just seems so messy. So here I am reaching out to you fine folks to pick your brains.
I want to look up HQLine and Description in the MPCC tab to return the correct MPCC Code. I tried a couple IF statements with VLOOKUPS but couldn't get it right.
So I need to look up BK3 Positive Crankcase Ventilation (PCV) Connector in the MPCC tab. So it needs to match BK3 and the Long description and then give me the correct code.
Here is the missing data file
Here is the MPCC export list that I want to search
Use SUMIFS.
SUMIFS will find the sum in a table of rows that meet certain criteria. If the MPCC is always a number, and the MQAb-LongDescription is always unique, SUMIFS will find the correct ID.
=SUMIFS(Sheet1!C$2:C$100,Sheet1!A$2:A$100,A2,Sheet1!B$2:B$100,B2)
where Sheet1!A$2:A$100 is the HQAb data, Sheet1!B$2:B$100 is the Long Description data, Sheet1!C$2:C$100 is the MPCC Number data, A2 is the HQLine, and B2 is the Description.
The formula would go in C1.
More information on VLookup with Multiple Criteria
You can use an Index/Match with multiple criteria.
I'm assuming that you will put this formula in "Sheet1", cell C2, and your lookup data is in a sheet called "Sheet2", columns A, B, C from row 2 to 30.
Put this in Sheet1, C2:
=INDEX(Sheet2!$C$2:$C$30,MATCH(A2&B2,Sheet2!$A$2:$A$30&Sheet2!$B$2:$B$30,0))
(Enter with CTRL+SHIFT+ENTER) and drag down.)
Adjust the ranges as necessary.
lets assume your first Table is on sheet 1 in the range A1:C11 and the MPCC codes are located on Sheet 2 in the range A1:C32. Each table has a header row so your data really starts in row 2.
Similar to BruceWayne's answer of using an array formula, you can bring the array calculation inside of a formula and avoid the special array treatment. There are a few functions that can do this. I will demonstrate with the SUMPRODUCT function;
On Sheet 1, Cell C2, use the following formula:
=INDEX('Sheet 2'!$C$1:C$32,SUMPRODUCT((A2='Sheet 2'!$A$2:A$32)*(B2='Sheet 2'!$B$2:B$32)*row('Sheet 2'!$A$2:A$32))
Explanation:
When the value in A2 matches the value in the range in the second sheet it will be true and false when it does not. when True False get used in math operations they are treated at 1 and 0 respectively. Therefore the only result from your two search criteria will be the rows where A2 match is true and B2 match is true and this will have a value of 1. The 1 will then be multiplied by the row number. Since all other results will be 0 since your list is a unique combination, the sum part of sumproduct will sum up to the row number where your unique row is located. This in turn is used by the indext function to return the row to give your unique number.

Set distinct drop-down values based on vlookup

Col A Col B
Fruit Grapes
Fruit Mango
Fruit Mango
Veg Carrot
Veg Brinjal
Fruit Banana
Veg Carrot
I have a similar requirement as shown in this thread
set drop-down values based on vlookup
This works fine, however now the requirement for me is in Column B there will be duplicates and the dropdown has to show only distinct values. Can any one help me with this
See file here Requirement
I want to achieve this by pure Excel formulas and not by VBA code.
Part 1 - This just shows how to create a unique list in a drop-down.
Here's a screenshot, but currently it requires that there is a row above the data(?). This provides a unique list of items in a Data Validation drop-down. (All the formulas below can be made easier to create by naming some ranges beforehand.)
The array formula in E2 is shown in the comment. Use Ctrl-Shift-Enter to enter an array formula, then drag this down as far as necessary - the #N/As will begin to appear at the bottom.
Gosh, it's hard to describe :). The COUNTIF essentially generates a sequence of 1s and 0s to indicate whereabouts in column B the previous (above) values in column E are positioned in column B. This sequence always starts with a 0 (for the formula in E2) because it's looking for a blank which doesn't occur in column B - so this will grab the first item, Grapes.
The MATCH then finds the first 0 in this sequence of 0s and 1s, which indicates that a value (in column B) hasn't already appeared in column E.
INDEX then uses this MATCHed value to retrieve the new unique item from column B.
Then a Defined Name is created (on the Formulas tab) that gets all the values in column E, but only down to the first occurrence of '#', which indicates there are no more unique values in the list.
This Defined Name is then used in the Data Validation.
Part 2 - The Answer (with VBA)
The following VBA code is required so that clicking in a cell in C11:C18 will change the value in F1, which generates the unique list underneath, which populates the data-validation list in C11:C18.
Private Sub Worksheet_SelectionChange(ByVal Target As Range)
If Not Application.Intersect(Target, Range("C11:C18")) Is Nothing Then
Sheets("Sheet1").Range("F1").Value = ActiveCell.Offset(0, -1).Value
End If
End Sub
It requires the formulas and defined-name as shown in the following screenshot. The formula in F2 is different to F3, which is then copied down.
The number 10 in the formula in F3 is just a large number (of rows).
Column E are the unique items.
Column D are the corresponding categories.
Column F are the unique items for the category in cell F1 (extracted form column E).
Part 3 - Without VBA
Use the formula =INDIRECT(ADDRESS(CELL("row"),CELL("col")-1)) in cell F1. When you click into a cell in C11:C18 you need to press F9 to recalculate the worksheet, which updates the drop-down list.
Recalculating is necessary to update the CELL("row") and CELL("col") values.
Part 4 - Without pressing F9
It can be achieved without having to press F9, but it means spreading all the categories across different columns (G1 and to the right in the below screenshot). This can also be achieved with the array formula =INDEX($A$2:$A$8,MATCH(0,COUNTIF($F$1:F1,$A$2:$A$8),0)) in G1.
The #N/As can also be removed the the drop-down lists with strategic use of IFERROR() in the formulas from G2 onwards, substituting "". Alternatively, using:
=OFFSET(Sheet1!$G$1,1,MATCH(Sheet1!B11,Sheet1!$G$1:$J$1,0)-1,MATCH("#",OFFSET(Sheet1!$G$1,1,MATCH(Sheet1!B11,Sheet1!$G$1:$J$1,0)-1,COUNTA(Sheet1!$G:$G)-1,1),-1),1)
as the defined-name Items would not only remove the #N/As but also the redundant ("") values that IFERROR() would leave in the drop-down lists. (The cursor needs to be positioned in C11 when creating this defined-name.)
Apologies for the length of this, but hope it is of interest to someone.

How to look up value in a column, and assign specific entries

I have a sheet in Excel where the columns contain different names of people that are in different teams in my department (i.e. Names in Column 1 are in Team 1).
For another sheet, I need to have a formula that achieves the following:If I write a name in Cell B2 that can be found in the first column of that other sheet (Team 1), Excel should populate cell B6 with "Team 1".
If instead, the name I wrote is found in the second column, then the text should read "Team 2".
I've tried a couple of different formulas w/o success, and stringing a lot of IF and OR functions together is way too cumbersome. Anybody has a better solution?
If you need this formula for more then only two column then id use the formula
=INDEX(Sheet1!C1:G1,SUMPRODUCT((Sheet1!C2:G6=B1)*COLUMN(Sheet1!C2:G6)))
Say you have a set-up like:
And in B1 of Sheet2 you enter Name3, you want it to return TEAM1 as shown below:
The only catch to this formula is that you will need to tell it how many columns are before your data so if you have a table more like:
Then you need to tell the formula that there are 2 rows before your data starts, your new formula will be
=INDEX(Sheet1!C1:G1,SUMPRODUCT((Sheet1!C2:G6=B1)*COLUMN(Sheet1!C2:G6))-2)
Notice the -2 before the last parenthesis this is to indicate that there are 2 columns BEFORE you data.
and the new result for looking up say NAME20 would become as follows:
*EXPLANATION: *
The formula works as follows , I will do it all on one page for easier viewing and instead of Sheet2!B2 and B6 I will use G2, and G6 on the same sheet as the data.
First we look at all values in the Range A1:E6 and find the one with the matching name so we use
=A1:E6=G2
Now when you enter this into the cell you will recieve a #VALUE,but if you goto the Formula Bar and press F9 it will shwo you the full value of the formula
{FALSE,FALSE,FALSE,FALSE,FALSE;FALSE,FALSE,FALSE,FALSE,FALSE;FALSE,FALSE,FALSE,FALSE,FALSE;FALSE,FALSE,TRUE,FALSE,FALSE;FALSE,FALSE,FALSE,FALSE,FALSE;FALSE,FALSE,FALSE,FALSE,FALSE}
In this we know that one cell contains the Name we searched for, this is represented by the TRUE
Now when using a formula like SUMPRODUCT, FALSE = 0 and TRUE = 1
So to get the column we mutiply every result by the column they are in.
=SUMPRODUCT((A1:E6=G2)*COLUMN(A1:E6))
So any cells that don't =G2 are FAlSE or 0, and when you multiply the column of that cell by 0 (because false = 0) it will simply result in 0. But for the one cell that IS TRUE or 1 When you multiply the column of that cell by 1 (because TRUE = 1) The product will be the cells column number
So as shown in the picture when looking for NAME13 the result of the sumproduct is 3 (its column)
Then to return the TEAM for that name, we use the INDEX function will return the value in a cell at the given cordinates.
In this case we want the value from A1:E1 that is in the same column as the Name we matched. When looked at as an Array A1:E1 looks like
{"TEAM1","TEAM2","TEAM3","TEAM4","TEAM5"}
And we want to return the value in that array at the same position as the column number of our cell, Minus any nonincluded column before the data, thus the reason for the -2 in the secon example I gave you.
So:
=INDEX(A1:E1,SUMPRODUCT((A1:E6=G2)*COLUMN(A1:E6)))
In this example excel interprets this formula as
Return the 3rd value (the 3 comes from the sumproduct as explained earlier) in the list of value from A1:E1. And that value would be TEAM3.
use a MATCH() or VLOOKUP() function inside an IF(). SOmthing like:
IF(NOT(ISERROR(MATCH(...)));"Team1";"")
Did you know you can browse functions by catergoty (such as Search), just clikc the fx left of your formula bar and use the drop down box. Each formula comes with a description with usually rather clear information...

Resources