I have a table of items with its buying and selling rates. Against each transaction, I wanted to show the item qty currently available and the current cost. Here is a screenshot of the table.
For the columns of Qty and Rate, I have used the formulas as shown below:
=SUMPRODUCT(C$2:C-F$2:F,B$2:B=B2,A$2:A<=A2)
=SUMPRODUCT(I$2:I/J2,B$2:B=B2,A$2:A<=A2)
Is it possible to convert SUMPRODUCT formulas as an array formula (returning array) so that it automatically fills whenever a row is added? Something like filling a column using FILTER or QUERY?
Regards,
Pravin Kumar.
I am making an assumption that this is your goal:
To automatically fill the quantity remaining column with the result of the difference between the two values, if and only if, there are two values provided.
A solution to this objective is:
=arrayformula(if(and(C2:C<>””, F2:F<>””), C2:C-F2:F, “”))
This produces a formula that subtracts C from F only if both C and F have values, and for all rows that have values in both C and F. If one of the rows does not have a value, the result will yield “” (blank). This formula should be posted at the top of the column where you want these results to start. In your screenshot example this would be cell J2. NOTE: 0 is still a value, and also that an array formula will not overwrite manually input data, so once you paste that function in J2, you will have to clear the cells below in order for it to auto populate.
Related
In my Google Sheet, I have 1000+ rows of Date entries. For each Date, I am calculating the Month# and Week# using MONTH() and WEEKDAY() functions respectively.
Here is the link to a sample file: https://docs.google.com/spreadsheets/d/1Af5-pYMFWZ1QtLoaAbPZYMGRvk43JBslUp4KyOFADfA/edit?usp=sharing
Problem Statement:
For all rows which have a unique Month# and Week#, I would like to implement a formula and calculate Output. For example, in my sheet, rows 3 to 6 pertain to Month=1 and Week=4. For this set of 5 rows I am calculating Output column as the subtraction from the first element in that set (ie... C3-$C$3, C4-$C$3, C5-$C$3 so on ). Similarly row 7 to 10 pertain to Month=1 and Week=5, and so I calculate Output
as Data-$C$7 and so on.
How do I implement this structure to calculate Output column on each set of unique Month# and Week# values?
Delete everything from Column F (including the F2 header). Then place the following formula into cell F2:
=ArrayFormula({"Output";IF(C3:C="",,IFERROR(C3:C-VLOOKUP(E3:E,{E3:E,C3:C},2,FALSE)))})
This one formula will create the header and return results for all valid rows.
Since VLOOKUP always finds only the first matching instance of what it is looking up, we can use it to ask that each value in C3:C subtract that first instance of where week-number match for each row.
By the way, although you didn't ask about this, you can also use this type of array formula in Columns D and E, instead of all of the individual formulas you have. To do that, delete everything from Columns D and E (including the headers). Then...
Place the following formula in D2:
=ArrayFormula({"Month #";IF(B3:B="",,MONTH(B3:B))})
... and the following formula in E2:
=ArrayFormula({"Week #";IF(B3:B="",,WEEKNUM(B3:B))})
In Google Spreadsheets, I want to read a cell containing the string 'e' into a formula which uses the 'e' as the horizontal component of a cell reference, eg 'e12'.
Hopefully clearer example:
a1 contains 'e'
a2 needs to contain 'e2'
then a2:a10 can contain 'eX' where X is 2 to 10.
I'm aware of the INDIRECT method, but I can't see how to use that to populate a2:a10 without a corresponding column of cells all containing 'e', one for each aX.
Perhaps I'm barking up the wrong tree.
I've got a table with list of names on the x axis and dates of meetings on the y axis. In each table element we have some string value to represent if they attended the meeting - eg "y" for attended the meeting "n" for did not, "a" for apologised for abscence in advance.
I also have a list, corresponding to the names on the x axis, of attendance, eg person1 has been to 60% of meetings. The trouble is that for every new meeting I insert a new column closest to the names list, and move all the other meetings one cell to the right. This means that for every new meeting, I have to update the formula with a new cell reference.
Before inserting a new meeting date, the formula looks roughly like DOSOMETHING(b2:y2). I then insert a column to the left of the b column. Google sheets cleverly updates the formula so to be DOSOMETHING(c2:z2), even though I really want the range to be b2:z2. I have tried DOSOMETHING($b2:y2), but inserting the column still causes this problem.
Thank you
instead of:
=DOSOMETHING(B2:Y2)
use this:
=DOSOMETHING(OFFSET($A2,0,1,1,99999))
the offset reference won't get messed up by the insertion of a column since it referrences column B by OFFSETing from column A. 99999 is just an arbitrarily large number that means "all the way to the right of the sheet.
you can read about offset here.
try like this in row 2:
=INDIRECT(A1&ROW()&":"&A1&10)
I'm trying to sum cell values based on an two adjacent cell values to help me organize/visualize my investment portfolio activity. I want to sum only the values in the cells under column B if the accompanying cell in column C and D meet a certain requirement.
Basically, for the values in B2:B1000, take the values for B(n) where C(n) equals "Deposit" and D(n) is equal to "Robinhood" and sum them. Below is a screenshot indicating the cells within column B that I want summed (in red) based on the criteria that meets both conditions. The below logic should give you the sum $1100.
I tried to at least check if C(n) equals Deposit with this line but then it just sums all of the values in column B.
=SUM(IF(C2:C1000=G2, B2:B1000, 0))
My guess is some of the cells in column C meet the condition it sums all of column B. That's the first problem. The second problem is I can't introduce the second condition without creating some sort of error.
My specific case is happening on google sheets.
Answer
Use SUMIFS(): =SUMIFS(B:B,C:C,"Deposit",D:D,"Robinhood")
My intention is to convert a single line of data into rows consist of a specific number of columns in Google Sheets.
For example, starting with the raw data:
A
B
C
D
E
F
1
id1
attr1-1
attr2-1
id2
attr2-1
attr2-2
And the expected result is:
(by dividing columns by three)
A
B
C
1
id1
attr1-1
attr1-2
2
id2
attr2-1
attr2-2
I already know that it's possible a bit manually, like:
=ARRAYFORMULA({A1:C1;D1:F1})
But I have to start over with it every time the target range is moved OR the subset size needs to be changed (in the case above it was three)!
So I guess there will be a much more graceful way (i.e. formula does not require manual update) to do the same thing and suspect ARRAYFORMULA() is the key.
Any help will be appreciated!
I added a new sheet ("Erik Help") where I reduced your manually entered parameters from two to one (leaving only # of columns to be entered in A2).
The formula that reshapes the grid:
=ArrayFormula(IFERROR(VLOOKUP(SEQUENCE(ROUNDUP(COUNTA(7:7)/A2),A2),{SEQUENCE(COUNTA(7:7),1),FLATTEN(FILTER(7:7,7:7<>""))},2,FALSE)))
SEQUENCE is used to shape the grid according to whatever is entered in A2. Rows would be the count of items in Row 7 divided by the number in A2 (rounded to the nearest whole number); and the columns would just be whatever number is entered in A2.
Example: If there are 11 items in Row 7 and you want 4 columns, ROUNDUP(11/4)=3 rows to the SEQUENCE and your requested 4 columns.
Then, each of those numbers in the grid is VLOOKUP'ed in a virtual array consisting of a vertical SEQUENCE of ordered numbers matching the number of data pieces in Row 7 (in Column 1) and a FLATTENed (vertical) version of the Row-7 data pieces themselves (in Column 2). Matches are filled into the original SEQUENCE grid, while non-matches are left blank by IFERROR
Though it's a bit messy, managed to get it done thanks to SEQUENCE() function anyway.
It constructs a grid by accepting number of rows/columns input, and that was exactly I was looking for.
For reference set up a sheet with the sample data here:
https://docs.google.com/spreadsheets/d/1p972tYlsPvC6nM39qLNjYRZZWGZYsUnGaA7kXyfJ8F4/edit#gid=0
Use a custom formula
Although you already solved this. If you are doing this kind of thing a lot, it could be beneficial to look into Apps Script and custom formulas.
In this case you could use something like:
function transposeSingleRow(range, size) {
// initialize new range
let newRange = []
// initialize counter to keep track
let count = 0;
// start while loop to go through row (range[0])
while (count < range[0].length){
// add a slice of the original range to the new range
newRange.push(
range[0].slice(count, count + size)
);
// increment counter
count += size;
}
return newRange;
}
Which works like this:
The nice thing about the formula here is that you select the range, and then you put in a number to represent its throw, or how many elements make up a complete row. So if instead of 3 attributes you had 4, instead of calling:
=transposeSingleRow(A7:L7, 3)
you could do:
=transposeSingleRow(A7:L7, 4)
Additionally, if you want this conversion to be permanent and not dependent on formula recalculation. Making it in run fully in Apps Script without using formulas would be neccesary.
Reference
Apps Script
Custom Functions
I'm learning basic =ARRAYFORMULA usage for a finance spreadsheet:
https://docs.google.com/spreadsheets/d/12cAGuUBzIo0LPbmtqWJZNFgjt94f1ybGoj6x2g0c2Y0/edit?usp=sharing
First, I used =GOOGLEFINANCE at B1 to pull up stock prices for a given date range in Column C
=GOOGLEFINANCE(A1,"price",DATE(2020,1,1),DATE(2020,5,30),"DAILY")
Then, I used simple arithmetic to multiply by number of shares at D2 and dragged the formulas down to get a nice column of values
=C2*20
Then, I used INDEX and COUNTA to pull out the last value of Column D at F3 === Great!
=INDEX(AAPL!D2:D,COUNTA(AAPL!D2:D),1)
Next, I turned my arithmetic formula into an ARRAYFORMULA at G2 === Cool!
=ARRAYFORMULA(C2:C103*20)
Of course, the problem with that ARRAYFORMULA is that I would have to manually change the array name in G2 every time the date range updated.
That is, instead of C2:C103, I would need to change the reference to C2:104 to get the columns to match === Rookie mistake!!!!!
So, I got smart with an ARRAYFORMULA containing a IF(ISBLANK(),...,...) at J2
=ARRAYFORMULA(IF(ISBLANK(B2:B),"",C2:C*20))
Column J stays fully populated with the correct values for any date range === !!!!!!!
But now the =INDEX(AAPL!J2:J,COUNTA(AAPL!J2:J),1) at L3 can't find the last value in Column J
Whaaat???
I've tried everything I can think of
It works if I use =INDEX(AAPL!J2:J104,COUNTA(AAPL!J2:J104),1) but that would defeat the purpose, since the reference J:J104 is going to change as the dates change
WHY???
I get the same results in both cells "L3" and "L5" when using:
=ARRAYFORMULA(IF(ISBLANK(B2:B),,C2:C*20))
Check that you are not returning a blank string ("") in your IF like: "=ARRAYFORMULA(IF(ISBLANK(B2:B),"",C2:C*20))" doing so will fill the cells up to the last row in the sheet with empty strings, thus when you use COUNTA(AAPL!J2:J),1) you get a lot more cells than you would expect, these extra cells are the ones you filled with blank strings in the array formula.
On the contrary when you limit the =INDEX(AAPL!J2:J104,COUNTA(AAPL!J2:J104),1) to cells with numbers only it doesn't mix strings and numbers in the calculation and you are naturally get the expected results.