Excel: How to check for repeated numbers inside a cell - arrays

I have an excel spreadsheet with numbers from 000 to 999 and am trying to find repeated numbers inside a cell.
(So for example, printing 1 if the number is 022 , 555 or 115 and 0 if it isn't)
So far, I have not been able to find a solution.
Feel free to ask for more information and thanks in advance.

This will do: =IF(COUNT(SEARCH(REPT({0,1,2,3,4,5,6,7,8,9},2),A1))>0,1,0)
Note: If value in cell A1 contains 2 repeated digits it will show 1 else 0. You can customize the repetition limit by changing 2 in the part 8,9},2).

You could try this one if you wanted to find repeated digits not necessarily next to each other:-
=IF(MAX(LEN(A1)-LEN(SUBSTITUTE(A1,{0,1,2,3,4,5,6,7,8,9},"")))>1,1,0)
If the numbers are stored as 3-digit numbers and you wanted it to work for (e.g.) 001, would need:-
=IF(MAX(LEN(TEXT($A1,"000"))-LEN(SUBSTITUTE(TEXT($A1,"000"),{0,1,2,3,4,5,6,7,8,9},"")))>1,1,0)

If your data is in Range "A1:A100" and you want to locate repeated numbers in the range for instance, enter =IF(COUNTIF(A:A,A1)>1,1,0) in cell B1 and fill down. But if you want to check repetitions of specific numbers like 022, 555 or 115, enter =IF(OR(AND(A1=022,COUNTIF(A:A,A1)>1),AND(A1=555,COUNTIF(A:A,A1)>1),AND(A1=115,COUNTIF(A:A,A1)>1)),1,0) in cell B1 and fill down.

being a number, use arithmetics to break it into digits and then check if all are different.
the formula is
=INT(NOT(AND(INT(A1/100)<>INT(MOD(A1,100)/10),INT(A1/100)<>MOD(A1,10),INT(MOD(A1,100)/10)<>MOD(A1,10))))
let's analyze it step by step
first, INT(A1/100) extracts the first digit (the integer division by 100); then INT(MOD(A1,100)/10) extracts the second digit (the integer division by 10 of the modulo 100); and MOD(A1,10) extracts the last digit (the modulo 10).
next there are the three comparisons of difference <> first with second, second with third and first with third, combined with AND() and finally take the result, negate it NOT() and transforming it into an integer 0 or 1 with INT()

Related

Issues with SUMPRODUCT in Excel: Trying to count the number of average subtractions above a given threshold

I have a fairly simple issue that I cannot seem to work out. It may be familiar to some of you now.
I have the following matrix (which I will refer to as two arrays):
F G H I J ... R S T U V
1 0 0 1 1
4 4 2 3 5 1 2 3 1 2
2 2 3 1 2 0 1
2 1 0 0 4 0 0 3 0 0
I would like to take the difference between the average of each row in array 1 (columns F:J) and the average of each row in array 2 (columns R:V). For example, the average of F2:J2 = 3.6, the average of R2:V2 = 1.8, and the overall difference = 1.8. I would then like to count the number of overall differences which exceed a given threshold (e.g., 1), but I want to ignore rows which have no entries (see R1:V1) and/or partially missing entries (see the 2nd entry in row F3:J3 and 4th and 5th entry in row R3:V3).
I was lucky enough to be introduced to array formulae by #Tom Sharpe, and have attempted to adapt his code for a similar issue I had, e.g.,:
=SUMPRODUCT(--((SUBTOTAL(1,OFFSET(F1,ROW(F1:F4)-ROW(F1),0,1,COLUMNS(F1:J1)))-SUBTOTAL(1,OFFSET(R1,ROW(R1:R4)-ROW(R1),0,1,COLUMNS(R1:V1)))>1)*(SUBTOTAL(2,OFFSET(F1,ROW(F1:F4)-ROW(F1),0,1,COLUMNS(F1:J1)))=COLUMNS(F1:J1))*(SUBTOTAL(2,OFFSET(R1,ROW(R1:R4)-ROW(R1),0,1,COLUMNS(R1:V1)))=COLUMNS(R1:V1))>0))
From what I understand, the code attempts to count the number of differences between the averages of each row in each array that exceed 1, so long as the product between the number of columns with full entries is >0 (i.e. has full data). However, it keeps throwing the #DIV/0! error, which I believe stems from that fact that it is still trying to subtract the average of F1:J1 and R1:V1 (e.g., the empty row), which would produce this kind of error. The correct answer for the current example is 1 (e.g., F2:J2 [3.6] - R2:V2 [1.8] = 1.8 == 1.8 > 1).
Does anyone have any ideas as to how the code can be attempted for the current purposes, and perhaps a v. brief explanation of what is going awry in the current code?
You're right, SUBTOTAL falls over when it's trying to find the average of an range containing only empty cells.
If you want to persevere and try and do it the same way as before with an array formula, you have to turn it round and put the condition for all the cells in both ranges to be non-blank in an if statement so that it doesn't try and take the average unless both ranges have no blanks:
=SUM(IF((SUBTOTAL(2,OFFSET(F1,ROW(F1:F4)-ROW(F1),0,1,COLUMNS(F1:J1)))=COLUMNS(F1:J1))*(SUBTOTAL(2,OFFSET(R1,ROW(R1:R4)-ROW(R1),0,1,COLUMNS(R1:V1)))=COLUMNS(R1:V1)),
--(SUBTOTAL(1,OFFSET(F1,ROW(F1:F4)-ROW(F1),0,1,COLUMNS(F1:J1)))-SUBTOTAL(1,OFFSET(R1,ROW(R1:R4)-ROW(R1),0,1,COLUMNS(R1:V1)))>1)))
This time unfortunately I found I couldn't SUMPRODUCT it - I think this is because of the presence of the IF statement - so you have to enter it as an array formula using CtrlShiftEnter
Will this work for you?
=IF(NOT(OR(IFERROR(MATCH(TRUE,ISBLANK(F1:J1),0),FALSE),IFERROR(MATCH(TRUE,ISBLANK(R1:V1),0),FALSE))), SUBTOTAL(1,F1:J1)-SUBTOTAL(1,R1:V1), "Missing Value(s)")
My approach was a little different from what you tried to adapt from #TomSharp in that I'm validating the cells have data (not blank) and then perform the calculation, othewise return an error message. This is still an array function call, so when you enter the formulas, press ctrl+shft+enter.
The condition part of the opening if() checks to see that each range's cells are not blank: if a match( true= isblank(cell))
means a cell is blank (bad), if no match ... ie no blank cells, Match will return an #NA "error" (good). False is good = Errors found ? No. ((ie no blank cells))

Convert big number to single digit array

So, I need to convert any number to its reverse and put it in an array.
For example:
123456789 --> [9 8 7 6 5 4 3 2 1]
I managed to do it for small numbers like the example with this:
n=32134654654213
rev=(fliplr(num2str(n)));
mikos=length(rev);
array=[ ]
for i=1:mikos
array=[array,str2num(rev(i))]
end
But when I put a big number like 564465426464334345413435541 the array is always 1x18 double and does not show all the digits.
Any ideas?
edit As you tell me in comments, it is a limit of how many digits a double can hold. You are right, if I use a string input, it works as a charm. Still wondering hot to make it work as a function, with this form :
function digits = GetDigits(n)
As mentioned in the comments, you have a limit on the number of digits a double can store. The limit on a uint64 is bigger (19), but still not sufficient to store your value. I would make sure it does not happen.
function digits = GetDigits(n)
%check if the value behaves as a normal integer
if isnumeric(n)
if n==(n+1),error('n too big, supply as string instead');end
end
rev=(fliplr(num2str(n)));
mikos=length(rev);
array=[ ]
for i=1:mikos
array=[array,str2num(rev(i))]
end
end

Using an Array to get the average of a selection of numbers

I have 12 different numbers on a row in an excel sheet (repeated few times on different row) and I would like to get the average of the 8 bigger numbers (4 numbers won't be used). I thought to use an array, but how to select the 8 bigger numbers in this array?
I would like to do it in VBA. Do you have any ideas/directions how to proceed, because I am not really sure how to start.
Example: 12,3,5,6,8,11,9,7,5,8,10,1 (Results=8.875), if I didn't make a mistake!
Thanks.
I know you asked for VBA, but here's a formula. If this works, you can quickly throw in VBA (use the macro recorder to see how if you're unsure).
If that's in row 1, you can use:
=AVERAGE(LARGE(A1:L1,{1,2,3,4,5,6,7,8}))
You should be able to change A1:l1 to be the range where your numbers are, i.e.
=AVERAGE(LARGE(A1:F2,{1,2,3,4,5,6,7,8}))
Edit: Per your comment, also no need for VBA. Just use conditional highlighting. Highlight your range of numbers, then go to Conditional Highlighting --> Top/Bottom Rules --> Top 10 Items. Then just change the 10 to 8, and choose a color/format. Then Apply!
(each row in the above is treated as it's own range).
Edt2: bah, my image has duplicate numbers which is why the top 8 rule is highlighting 9 numbers sometimes. If you request I'll try to edit and tweak
You can use a simple Excel function to compute the answer
=AVERAGE(LARGE(A1:L1, {1,2,3,4,5,6,7,8}))
It is a bit more complex in VBA, but here is a function that does the same computation (explicit typing per Mat's Mug):
Public Function AvgTop8(r As Range) As Double
Dim Sum As Double, j1 As Integer
For j1 = 1 To 12
If WorksheetFunction.Rank(r(1, j1), r) <= 8 Then
Sum = Sum + r(1, j1)
End If
Next j1
AvgTop8 = Sum / 8#
End Function
The Excel RANK function returns the rank of a number in a list of numbers, with the largest rank 1 and so on. So you can search through the 12 numbers for the 8 largest, sum them and divide by 8.
You don't need VBA for this. You can use:
=AVERAGE(LARGE(A1:L1,{1;2;3;4;5;6;7;8}))

Excel: Fill a range of cells with a value or formula depending on only one cell

We have a project on a certain math subject and I am done with the computations and it works just fine. So the task is, let's say you have a system of linear equations of certain number of unknowns, you input the number of unknowns, and fill in the values, and using matrix computations, find all the value of unknowns.
To make this short, I already finished the "find the value of unknowns" along with the computation, I checked it, and it seems fine. I can put 6 as the number of unknowns and it automatically computes the inverse of a 6x6 matrix and it will return the 6 unknown values using Index INDIVIDUALLY.
(Note: We aren't allowed to use VBA or Macros since we haven't discussed that yet.
The problem is, I don't know how to automatically fill a RANGE of cells with a VALUE or A FORMULA based on a SINGLE cell value.
For example, In cell A1, I will input 5 (which indicates the number of unknowns), then upon inputting this and hitting enter, let's say a range of cells A2 to A6 (which is 5 cells) will be automatically filled with incremented letters, like for A2 -> A ; A3 -> B ; ... A6 -> E, of which these letters indicate the 5 unknowns.
PROBLEM 2.
Another follow up question, let's say I input again 5, which again stands for the number of missing values/unknowns, in A1, besides the column of the variables A,B,C,D,E (5 unknowns), I want to automatically fill column B respectively with values from an array.
This is just the same with my first problem but this time, instead of incremented letters, it would be Incremented Index function.
For example: I input 5
*Column A will automatically be filled with the variables/letters
*Column B will automatically be filled with the values from an array that's computed using a formula but is not shown independently on cells.
I already have the formula
INDEX(Formula I created, Row number of the answer from the Formula I created , Column number of the answer from the formula I created)
The answers from the formula I made myself is also an array, an "n" rows and 1 column array. If I put the Index formula on a SINGLE cell, it returns specified row number value from the array that resulted in the computation from my formula
What I want is for example, for 5 unknowns
**A | B**
1|.......5..........................
2|.......A..............Some Value 1
3|.......B..............Some Value 2
4|.......C..............Some Value 3
5|.......D..............Some Value 4
6|.......E..............Some Value 5
Wherein the "Some Value" is the Arrayed Answer from my formula and the "1,2,3,4,5" specifies the row number from that arrayed answer.
This is upon inputting the matrix values, inputting the number of unknowns "n" in A1, and automatically filling a range of cells A2 to A"n" with letters A up to what letter "n" corresponds, and automatically filling a range of Cells B2 to B"n" with my formula but with incremented row number for every row in the Index(Formula, Row number , Column number) function.
Note: I hope there's a way to do this using excel functions only since we haven't discussed VBA or Macros yet so we can't use those, and even If we can, I have no knowledge for that. haha. :D
THANK YOU THANK YOU THANK YOU SO MUCH IN ADVANCED! Cheers. :D
Here's a formula for column A:A (write this in cell A2) and drag down:
=IF(ROW()-1<=$A$1,CHAR(ROW()+63),"")

Using binary strings on storing ordered items in database

In this post, #boisvert mentioned that if using string as the order field's value, it is best shown for a binary string, and then gave an algorithm to calculate the average of two binary strings as follows:
Avalue = 1+0*(1/2)+1*(1/4)+1*(1/8)
Bvalue = 1+1*(1/2)+0*(1/4)+0*(1/8)
average, new value = 1+0*(1/2)+1*(1/4)+1*(1/8)+1*(1/16) new string = "10111"
content order
--------------------
A '1011'
new! '10111'
B '1100'
C '1101'
I couldn't understand these very well, what's the value of the first item putting into the DB and the items inserting before/after it? How to calculate the average between '1011' and the new value '10111', or between '111' and '1000'?
Any help is much appreciated.
The binary strings are fractions, not integers; the decimal point is always at the beginning (or after the first digit, in #boisvert's answer; it doesn't make any difference as long as the position of the decimal point is fixed. Of course, it's actually a binary point since these are binary numbers.)
To find the average:
If the strings differ in length, put enough 0s at the end of the shorter string so that it is the same length as the longer string.
Add the two strings together, using binary addition, always putting the last carry at the beginning, even if it is ยด0'. [See algorithm below].
Remove any 0s at the end.
Example 1: 1011 and 10111
Extend the first string with a 0: 10110 and 10111
Find the sum:
A: 10110
B: 10111
Carry: 101100
Sum: 101101
No trailing zeros, so the result is 101101
Example 2: 111 and 1000
1. 1110 1000
2. 10110
3. 1011
Starting off and insertion at the end:
The first item put into the database has the label 1. If at any point you need to add an item at the very beginning, use the first label with a 0 before it. Similarly, if you need to add an item at the end, use the first label with a 1 before it.
Binary addition:
Since the strings are the same length, this is easy; set Carry to 0, and scan both strings from back to front. (The output is also produced back-to-front.)
At each position:
* If the sum of Carry and the two digits is 1 or 3, output a 1, otherwise output a 0.
* If the sum of Carry and the two digits is 2 or 3, set Carry to 1, otherwise set it to 0.
When you've finished all the digits, output the value of Carry.
Practical implementation:
In practice, you wouldn't use binary strings; you'd use some fairly large base, the only requirement being that it is even. But the algorithms are the same. When constructing the representation of your numbers, you need to assign digits to characters in alphabetical order, so that the resulting strings can be sorted alphabetically without converting them to numbers; the database doesn't know how to convert to numbers, but it knows how to sort strings alphabetically.

Resources