I want to sum the total value preceding a lookup value in a range with a defined starting point. can anyone clue me into why this formula wont work?
=SUM(E9:CELL("address",INDEX(E9:BN9,MATCH("130LSR",E9:BN9,0))))
The result from just the cell function works:
=CELL("address",INDEX(E9:BN9,MATCH("130LSR",E9:BN9,0)))
This returns $F$9 in my sheet which is correct. It also has the workbook and sheet references prior, is that my problem? is there a way to remove the book and sheet references? The sum function obviously works if I provide the address, but why can't i define the end of my range with the cell(address) formula?
Related
I'm trying to use structured references to the current columns the same as CountIf does for my UDF function. While
=COUNTIF(Data[Team];Overview[Team])
works, my new function
=CONCATENATEIF(Data[Team];Overview[Team];Data[Data])
doesn't work, since the Overview[Team] criteria Range can't be cast to a single value which is [#This Row].
I tried to change the parameter "criteria" As String as well as different methods. Calling
=CONCATENATEIF(Data[Team];Overview[#Team];Data[Data])
with "#" works as intended. But CountIf can handle [#Team], [Team] and normal ranges like [A1:A4]. So how they do it?
Public Function CONCATENATEIF(check_range As Range, criteria As Range, data_range As Range) As Variant
Dim mydic As Object
Dim L As Long
Set mydic = CreateObject("Scripting.Dictionary")
For L = 1 To check_range.Count
If check_range(L) = criteria Then
mydic(L) = data_range(L)
End If
Next
CONCATENATEIF= Join(mydic.items, ", ")
End Function
What cast does criteria need to work like CountIf's criteria? How can i transform the structured Reference [Team] to [#Team] vba-wise, so it selects the same row, where the Formular is used later.
The table for the problem (sadly can't embed images yet)
COUNTIF works due to inferred reference¹.
If you put a bunch of values in column A and then use =INDEX(A:A, , ) (Index(<column_A>, <all_rows>, <all_columns>)) in an unused column to the right of the data then the result will be from the common row in column A. Since you haven't provided a specific row reference where a single cell reference is expected, the associated (or inferred) row is used. This is why COUNTIF works; it is using an inferred reference from the Overview[Team] column to reference a single cell for criteria; e.g. the cell in Overview[Team] that is on the same row as the formula (also known as Overview[#Team]).
The VBA code is not using an inferred reference. It is referencing the whole column of Overview[Team] where it needs a single cell for criteria (e.g. Overview[#Team]).
You could try to artificially parse the column of criteria down to a single cell with something like Application.Caller.Row or you could just use Overview[#Team] as the criteria like it was intended.
¹ I hope I got that term right. I use it so little that I have a hard time remembering the correct term sometimes.
Suppose that I have Excel workbook with two sheets, lets name them 'sheet one' and 'sheet two'. I want to perform a summation in range from cell 'sheet two'!R125C('sheet one'!R2C4+6) to cell 'sheet two'!R137C('sheet one'!R2C4+6) in R1C1 notation. So my goal is to have a sum which columns range depends from given cell.
I tried
=SUM('sheet two'!ADDRESS(125;R2C4+6;1;0):'sheet two'!ADDRESS(137;R2C4+6;1;0))
but it doesn't work (I can't see my mistake). Maybe it is also possible to perform this task using INDIRECT function. So, what is the proper way to evaluate sum which range depends from a value in a cell?
Any help will be very appreciative.
UPDATE: I also tried
=SUM(INDIRECT("'sheet two'!R125C"&R2C4+6&":'sheet two'!R137C"&R2C4+6;FALSE))
and it returns me an #REF! error.
I have successfully solved my problem with the help of different approach. I just searched through the head of table in my 'sheet two' with MATCH function and returned column index, then substituted it into INDIRECT and SUM functions.
The full working function is
=SUM(INDIRECT("'sheet two'!R125C"&MATCH("Total number";'sheet two'!R2;0);FALSE):INDIRECT("'sheet two'!R137C"&MATCH("Total number";'sheet two'!R2;0);FALSE))
My understanding is that you can define a range using index. example I can set a defined name of MyList to
=index(A:A,3,1):index(A:A,5,1)
This would be the equivalent of saying A3:A5. I can then turn around and use index(MyList,1,1) and I would see the contents of A3. All this works for me.
So I was trying to define a range of sheet names. I used defined name sheetnames as:
=TRANSPOSE(GET.WORKBOOK(1,Structural!$J$3)&T(NOW()))
(I used transpose to get the list vertical)
when I use:
=INDEX(Sheetnames,3,1)
=INDEX(Sheetnames,6,1)
I get the name of my 3rd or 6th sheet in my workbook respectively. So that part is working. However when I try to define a range like I did for MyList using the following I get #value
=INDEX(INDEX(Sheetnames,3,1):INDEX(Sheetnames,6,1),1,1)
QUESTION:
Why is it not working?
As a test to get first sheetname I have also tried:
=OFFSET(Sheetnames,1,1,1,1)
This also gave the same error.
What I am ultimately trying to do is generate a pull down list through data validation of all sheet names except the sheets named "Index" and "Master".
As per Excel's help file on INDEX...
Reference form
Description
Returns the reference of the cell at the intersection of a particular
row and column. If the reference is made up of nonadjacent selections,
you can pick the selection to look in.
Syntax
INDEX(reference, row_num, [column_num], [area_num])
The INDEX function syntax has the following arguments.
Reference Required. A reference to one or more cell ranges
etc...
Therefore, in order to return a reference, you would need to reference a range of cells. SheetNames, however, doesn't refer to a range of cells. It refers to GET.WORKBOOK, which returns an array of values. In this case, it returns an array of sheet names.
So with the following formula...
=INDEX(INDEX(Sheetnames,3,1):INDEX(Sheetnames,6,1),1,1)
...it gets evaluated as follows (assuming the workbook is called Book1.xlsx and you have Sheet1, Sheet2, Sheet3, etc)...
--> some preliminary evaluations <---
=INDEX("[Book1.xlsx]Sheet3":"[Book1.xlsx]Sheet6",1,1)
=INDEX(#VALUE!,1,1)
=#VALUE!
You can evaluate the formula for yourself by selecting the cell containing the formula, and stepping through it using the Evaluate Formula button on the Ribbon (Formulas tab > Formula Auditing group).
You can also confirm that INDEX doesn't return a reference in this case by using the ISREF function. The following formula should return FALSE...
=ISREF(INDEX(Sheetnames,3,1))
Hope this helps!
I am using the following code to sum all the numbers in different columns. The formula always gives me wrong answer. Please help! Thanks
Sub TOTALVALNEW(colNumber As Integer)
Dim StartOfTheRANGE As Range
Dim EndOfTheRange As Range
Set StartOfTheRANGE = Evaluation.Cells(3, colNumber)
Set EndOfTheRange = StartOfTheRANGE.End(xlDown)
'Evaluation is the name of the sheet.
Evaluation.Cells(3, colNumber).End(xlDown).Offset(1, 0) = Application.Sum(StartOfTheRANGE, EndOfTheRange)
End Sub
VBA's Application.Sum works exactly the same as the worksheet function SUM() in a cell formula. It takes an object, or a list of objects. If you specify two objects namely the first and last cells, it will just take the sum of the values of the contents first and last cells only (a 2-term sum), not anything in between. If you want to include all cells between the first cell and last cell inclusive, you need to make make a range object by using the Range() function. So changing to this:
Evaluation.Cells(3, colNumber).End(xlDown).Offset(1, 0) = Application.Sum(Range(StartOfTheRANGE, EndOfTheRange))
should work.
The data in column A looks like this.
RowHeaderThatIsText
RowHeaderThatIsNumber
empty
empty
empty
empty
empty
14.00
-3.00
-4.00
The project goal is to to calculate summary statistics for the series of numbers and update the summary each month.
My goal is to allow a new number to be added to the series and have the summary update automatically.
Here's what I've done so far.
Define a range named LastCell with the formula
=INDEX($A:$A, MAX(($A:$A <> "") * (ROW($A:$A))))
This returns the last non-empty cell in the column. The data to summarize is always the last block of numbers.
Define a named range called HeaderOffset with the formula
=3
Used in the step 3.
Define a range named FirstCell with the formula
=OFFSET(LastCell, HeaderOffset - COUNTA($A:$A), 0)
This returns the first cell of the last block of numbers if, as is the case with the data I'll be summarizing, the cells between the first and last blocks are empty.
Define a range named DataBlock with the formula
=FirstCell:LastCell
So far so good. This allows one to enter =SUM(DataBlock) into any cell and get the expected result of 7.00. And, if I add another value, say 3.00, to the list the SUM result will update to 10.
The part I don't like is HeaderOffset. If another row is added to the header, HeaderOffset needs to be updated from =3 to =4. What if I forget to update HeaderOffset? This lead me to the problem I can't currently solve...
Is there an Excel formula that, given the ending cell, returns the starting cell of a block of data? Basically I'm looking for a FirstCell formula that removes the need for HeaderOffset.
As a bonus I was trying to do this whole thing without using volatile Excel functions. I failed by using OFFSET. Solving this is great. Solving it without volatile functions is ideal.
Is FirstCell always the first number? If so try this to define FirstCell
=INDEX($A:$A,MATCH(TRUE,ISNUMBER($A:$A),0))
That's an "array formula" if entered on the worksheet but doesn't need any special treatment if used in the "refers to:" box to define a named range.
Note: if your final aim is the sum of the numbers then could you just use =SUM(A:A) [I assume that's oversimplifying the issue?]
Revised given comment below:
Try this for LastCell
=INDEX($A:$A,MATCH(9.99E+307,$A:$A))
and this one for FirstCell
=INDEX($A:$A,MATCH(2,1/($A$1:LastCell=""))+1)
assumes LastCell is numeric (although that can be changed if required)