I need a little help, I have an Excel book with a long list of customers and in the adjacent cell is ether a 1 or 0 depending if the customer has ordered in the past month.
How can I split this list into 2 lists on another page one been ordered in the past month and the other not ordered,
Im unable to use Macros due to security levels on the PC.
Thanks
Try,
'for ones
=INDEX(A:A, AGGREGATE(15, 7, ROW(B$2:INDEX(B:B, MATCH(1E+99, B:B)))/(B$2:INDEX(B:B, MATCH(1E+99, B:B))=1), ROW(1:1)))
'for zeroes
=INDEX(A:A, AGGREGATE(15, 7, ROW(B$2:INDEX(B:B, MATCH(1E+99, B:B)))/(B$2:INDEX(B:B, MATCH(1E+99, B:B))=0), ROW(1:1)))
Of course, you will have to modify to suit the different worksheet.
See the image below. Using array formulas (Ctrl+Shift+Enter) I entered this into D2:D8:
=IFERROR(INDEX(A2:A8,SMALL(IF(B2:B8,ROW(A2:A8)-ROW(A1)),ROW(A2:A8)-ROW(A1))),"")
and this into E2:E8:
=IFERROR(INDEX(A2:A8,SMALL(IF(1-B2:B8,ROW(A2:A8)-ROW(A1)),ROW(A2:A8)-ROW(A1))),"")
Explanation
This is how Excel will calculate the first formula:
=IFERROR(INDEX(A2:A8,SMALL(IF(B2:B8,ROW(A2:A8)-ROW(A1)),ROW(A2:A8)-ROW(A1))),"")
=IFERROR(INDEX(A2:A8,SMALL(IF({1;0;1;0;0;0;1},{2;3;4;5;6;7;8}-1),{2;3;4;5;6;7;8}-1)),"")
=IFERROR(INDEX(A2:A8,SMALL(IF({1;0;1;0;0;0;1},{1;2;3;4;5;6;7}),{1;2;3;4;5;6;7})),"")
=IFERROR(INDEX(A2:A8,SMALL({1;FALSE;3;FALSE;FALSE;FALSE;7},{1;2;3;4;5;6;7})),"")
Since the second argument of SMALL is an array, it will find the 1st, 2nd, 3rd, etc. value, ignoring FALSE (it will return #NUM! for the 4th through 7th value).
=IFERROR(INDEX(A2:A8,{1;3;7;#NUM!;#NUM!;#NUM!;#NUM!}),"")
=IFERROR({"A";"C";"G";#NUM!;#NUM!;#NUM!;#NUM!},"")
={"A";"C";"G";"";"";"";""}
Related
I have a list of values between 1 and 100, essentially a sort of ranking that occassionally skips a few numbers (for example, the first ten values are 2, 6, 6, 10, 10, 10, 10, 11, 12, 13). They're ordered ascendingly, so every number will be either higher than or equal to the number above it. Now, I wish to remove all the duplicates from this list while remaining between 1 and 100. So, for example, for the values above, something like 2, 6, 7, 10, 11, 12, 13, 14, 15, 16 would work or 2, 6, 7, 8, 9, 10, 11, 12, 13, 14. However, the formulas I've tried so far will either go over 100, go under 1, or create circular references.
Given the nature of the list, there's very little chance of the amount of values exceeding 100, so if that possibility can be accounted for, it'd be a nice bonus, but it's not required.
Please create a named range for all your numbers and name it Source. As an alternative, replace the named range Source in my formulas below with the sheet address of the range where you have your numbers.
[C2] =INDEX(Source,MATCH(0,COUNTIF($C$1:$C1,Source),0))
This is an array formula and needs to be confirmed with Ctl + Shift + Enter. Observe that the COUNTIF range is defined one row above the row in which the formula resides. Its formulated with one absolute and one relative end. The end of the range will expand as you copy the formula down.
You can achieve a similar result using the LOOKUP() function. But since MATCH() finds the first instance, LOOKUP() returns the last. Therefore the formula below will return the same sequence in descending order. LOOKUP() is capable of looping on its own and the formula doesn't require array enabling. Just confirm it normally, with only Enter.
[E2] =LOOKUP(2,1/(COUNTIF($E$1:E1,Source)=0),Source)
Observe that the result range is defined with an absolute and relative end, starting above the row of the formula as explained above.
In B2, formula copied down :
=IF(A2="","",IF((COUNTIF(B$1:B1,A2)>0)+(A2=A1),B1+1,A2))
Edit #1
If data have repeated 100 as per OP's comment, then B2 formula become :
=IF((COUNTIF(B$1:B1,100)>0)+(A2=""),"",IF((COUNTIF(B$1:B1,A2)>0)+(A2=A1),B1+1,A2))
Thank you everyone for posting! Thanks to Bosco's original reply, I managed to fiddle around and find the answer myself. The biggest issue I was facing was getting a circular formula error, but by using Bosco's formula as a help column I was able to get it all worked out.
So, the solution holds 3 different columns: Original Data (column A), Help Column (column B) and Final Result (column C).
In the Help Column, I did as suggested, in cell B2 and copied down:
=IF(A2="","",IF((COUNTIF(B$1:B1,A2)>0)+(A2=A1),B1+1,A2))
This would occassionally create results over 100, so in the Final Column I placed the following array formula, which incidentally also accounts for lists longer than 100 entries, in C2 and copied down:
=IF(B2="","",IF(ROW(C2)>101,ROW(C2),IF(AND(B2>=100,B3=""),100,IF($B2:$B$1000>=C3,C3-1,B2))))
As an array formula, this needs to be entered using Ctrl+Shift+Enter.
Thank you very much to everyone who posted replies, I'm sorry for my lack of clarity!
So in the example above, I would like to extract all cells that contain "A" as the first letter(and length=9, though it does not matter). Now I am able to run the function for one cell, but I want to run it as an array formula so that I do not have to drag down 1000 cells every time. Below is my code:
=IFERROR(INDEX($A$1:$A$3, IF(AND(LEFT(A2,1)="A", LEN(A2)=9), ROW($A$1:$A$3),"")),"")
The problem here is that when I enter the code with "Ctrl + Shift + Enter", the criteria would be only confined to A2, which is the cell address I manually entered. Is there anyway to check for every single cell without having to drag down WITHOUT USING VBA? I know using VBA would make it a lot easier, but I just want to understand the basics of Excel further.
Try,
=iferror(index(a:a, aggregate(15, 7, row(a:a)/(left(a$1:index(a:a, match("zzz", a:a)))="a"), row(1:1))), text(,))
'with 9 length criteria
=iferror(index(a:a, aggregate(15, 7, row(a:a)/((left(a$1:index(a:a, match("zzz", a:a)))="a")*(len(a$1:index(a:a, match("zzz", a:a)))=9)), row(1:1))), text(,))
Fill down as necessary.
If you only want the single left-most character from a string of text, you do not have to supply a 1; you can omit the number of characters argument.
I need to get the top 6 repeating numbers in columns A-F , in any order would be fine , tried using =Mode but I'm stuck
You can use =TRANSPOSE and =MODE.MULT
This is an array formula, close with CTRL+SHIFT+ENTER:
=TRANSPOSE(MODE.MULT(A:F))
And fill across 6 cells to get the top 6 repeating values.
The MODE function is not the most efficient formula, likely due to some internal cyclic calculation. Cut your full column ranges down to the minimum of what is required for an accuate result.
In K12 as a standard formula,
=mode(a:f)
'better as,
=mode($A1:INDEX($F:$F, MATCH(1E+99, $F:$F)))
In L12 as an array formula with CSE,
=MODE(IF(NOT(COUNTIF($K12:K12, $A1:INDEX($F:$F, MATCH(1E+99, $F:$F)))), $A1:INDEX($F:$F, MATCH(1E+99, $F:$F))))
Fill L12 right to P12.
Recommended: MINIF, MAXIF and MODEIF
I'm trying to build a MATCH formula (or a similar one) that returns the position of the first value (date) within a range that matches a specific year.
For example, if I have a list of dates, like this:
A
1 12-31-2014
2 11-30-2015
3 12-29-2016
4 12-30-2017
For the value 2016, it should return 3.
MATCH(2016,A:A,0) doesn't work, since it's not an exact match. I can't use any aux columns either nor modify the dates.
Any ideas?
Are you allowed to use array formulas? If so, it may be as simple as this:
=IFERROR(MATCH(2016,YEAR($A$1:$A$4),0),"No Match")
Remember to commit the answer using Ctrl+Shift+Enter, since it'll be an array.
You'll want to change the references within the YEAR function to match your range. By using 0 as your [match_type] parameter, you're going to get the first value in the list that has a year of 2016.
For real dates, try,
=aggregate(15, 6, row($1:$999)/(year(a$1:a$999)=2016), 1)
'return the date with index as,
=index(a:a, aggregate(15, 6, row($1:$999)/(year(a$1:a$999)=2016), 1))
If they are in ascending order you could use,
=MATCH(42369, A:A)+1
=index(a:a, MATCH(42369, A:A)+1)
For a list of strings that look like dates try,
=MATCH("*2016", A:A, 0)
=index(a:a, MATCH("*2016", A:A, 0))
I need to return a cell that has text in it, but am running into difficulty.
Above is a sample table I'm working with. What I'd like to be able to do, is lookup id 1 and have it output Rich. When I do a vlookup, however, it gives no output. And while vlookup min/max will output integers, they don't work with text. Does anyone know how I can scan multiple ids, but only output the filled text cell?
There may be a shorter formula for this but I banged this off quickly and it does dynamically truncate the ranges in column B down to the minimum number of rows necessary.
=INDEX(B:B, AGGREGATE(15, 6, ROW(B2:INDEX(B:B, MATCH("zzz",B:B )))/(ISTEXT(B2:INDEX(B:B, MATCH("zzz",B:B )))*(A2:INDEX(A:A, MATCH("zzz",B:B )))=D3), 1))
To retrieve a second, third, etc. entry change the k parameter of AGGREGATE to a COUNTIF and fill down.
=INDEX(B:B, AGGREGATE(15, 6, ROW(B$2:INDEX(B:B, MATCH("zzz",B:B )))/(ISTEXT(B$2:INDEX(B:B, MATCH("zzz",B:B )))*(A$2:INDEX(A:A, MATCH("zzz",B:B )))=D3), COUNTIF(D$3:D3, D3)))