Formula for Auto Generating number in Google Spreadsheet - google-sheets

I am trying to find the way of making a formula that will auto generate the "id" number like we do in mySql auto-generate.
If I explain more, it would be like (number of A1 + 1).

You can try this formula,
=SUM((INDIRECT("A" & ROW() - 1)),1)
Here A is the column.
How it works:
You have to put a number on a cell of A column then the very next row of that A column you will put this Formula. Then you should get the number + 1. Which will look like MySql auto generated id.
Then you can just grab the blue dot/point of the cell which is lower right of the cell, and expand it to lower of the A column, and it will generate numbers like MySql auto generated id.

use SEQUENCE:
=SEQUENCE(10)
bound to A column:
=SEQUENCE(COUNTA(A2:A))

Related

How to skip row for user input using formula?

Given the following table:
I was able to find a formula that adds a blank row after each row for the 'Track Name' column, which allowed me to populate the new table (see expected output) correctly with ArrayFormula into merged cells.
={"Track Name";ARRAYFORMULA(IFERROR(VLOOKUP(ARRAY_CONSTRAIN(ROW(Data!A2:A),COUNTA(Data!A2:A)*2-1,1), {IF(LEN(Data!A2:A),ROW(Data!A1:A)*2,),Data!A2:A},{2},FALSE)," "))}
Now, is it possible to then use ArrayFormula to retrieve the artists & features while skipping rows to allow for user input?
Expected output:
I could probably set this up using a script, but if I can avoid that then I think that'd be better...
Try:
=ArrayFormula(iferror(vlookup(array_constrain(row(A2:A),COUNTA(A2:A)*2-1,1),{if(len(A2:A),row(A1:A)*2,),ArrayFormula(split(ArrayFormula(B2:B & "," & C2:C),","))},{2,3,4,5},false)," "))
Result:
For the merged cells for the Track Name column I'm assuming you've formatted this manually.
To explain this I've used this formula from the reference link:
=ArrayFormula(iferror(vlookup(array_constrain(row(A2:A),COUNTA(A2:A)*2-1,1),
{if(len(A2:A),row(A1:A)*2,),B2:C)},{2,3},false)," "))
I replaced the range B2:C with the formula from this post ArrayFormula with TextJoin of a row of columns to join columns B and C and split them to multiple columns. I also changed the {2,3} to {2,3,4,5} (you need to change this if you are expecting more columns).
NOTE: This does not work for merged cells it is only displaying the value on the left cell if you have 2 horizontally merged cells.
Please see the reference link below if you need more information on the formula used.
Reference:
Refer to this link for more detailed explanation: Insert Blank Rows

Implement formula in a column based on contents of each cell

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))})

Transpose a table row by row

I need to transpose parts of a table row by row. The following example illustrates what the result needs to look like:
I tried different combinations of arrayformula(), flatten() and transpose(), succeeded with getting the last column right with =arrayformula(FLATTEN(B4:C)), but need now help with fixing this.
Link to table
Try this in row 2 of the example screenshot:
={flatten({A2:A,A2:A}),arrayformula(flatten({if(A2:A<>"",B$1,),if(A2:A<>"",C$1,)})),flatten({B2:C})}
Or if you want the column headings, put this in row 1:
={"A","B","C";flatten({A2:A,A2:A}),arrayformula(flatten({if(A2:A<>"",B$1,),if(A2:A<>"",C$1,)})),flatten({B2:C})}
The new column 'C' ends up being a mixed data type, so be careful if you run a future query on these results as it doesn't like mixed data.
For local implementation (as per your initial screengrab, EU locale file), try this in cell E4 - since the formula sits in row 4, the array range needs to go from 4 (A4:A):
={flatten({A4:A\A4:A})\arrayformula(flatten({if(A4:A<>"";B$3;)\if(A4:A<>"";C$3;)}))\flatten({B4:C})}
Alternatively, if you want column headings, try this in cell E3 - the array range is still A4:A because "A"\"B"\"C"; puts headings in row 3, ; is a return, then the rest of the formula targets data from row 4 down:
={"A"\"B"\"C";flatten({A4:A\A4:A})\arrayformula(flatten({if(A4:A<>"";B$3;)\if(A4:A<>"";C$3;)}))\flatten({B4:C})}
If you want to limit the array range to a specific row rather than working down the entire sheet (eg. row 20), then A4:A would need to be A4:A20.
This is a basic SPLIT(FLATTEN( problem.
Arrayformula() can always exist on the outside of a formula and will apply to the whole thing.
This is on a new tab in your sample called MK.Help:
=ARRAYFORMULA(QUERY(TO_TEXT(SPLIT(FLATTEN(Data!A2:A&"|"&Data!B1:C1&"|"&Data!B2:C);"|";0;0));"where Col1<>''"))

conditional formatting to check every nth of column

I try to add conditional formatting using custom formula. I want to check if in a single row (in this case, in row 5 and it starts from column L and skip every 3rd column: L, P, T,....), there's at least one not empty shell.
The formula below works perfectly. It's only it's not dynamic, I mean in case I add more column to check then I have to add more and more "+ not(isblank(...))" there and become very long. Is there any shorter formula which should be checked no matter the last column is.
=(not(isblank(L5))+ not(isblank(P5))+ not(isblank(T5)) +not(isblank(X5)) + not(isblank(AB5)) +not(isblank(AF5)) + not(isblank(AJ5))+ not(isblank(AN5))+not(isblank(AR5))+not(isblank(AV5))+ not(isblank(AZ5)) ) > 1
here's the link:
https://docs.google.com/spreadsheets/d/1kedGsLIUw2UsA8LbiWe0w_s9HYoBLqOl6zGQxZlLq5s/edit#gid=0
you can do it like this which is shorter but still not dynamic:
=((E2<>"")+(I2<>"")+(M2<>"")+(Q2<>"")+(U2<>"")+(Y2<>"")+(AC2<>"")+(AG2<>"")+(AK2<>"")+(AO2<>"")+(AS2<>"")+(AW2<>"")+(BA2<>"")+(BE2<>"")+(BI2<>"")+(BM2<>"")+(BQ2<>"")+(BU2<>"")+(BY2<>"")+(CC2<>"")+(CG2<>"")+(CK2<>"")+(CO2<>"")+(CS2<>"")+(CW2<>"")+(DA2<>"")+(DE2<>"")+(DI2<>"")+(DM2<>"")+(DQ2<>""))>1
this will cover 30 columns (the equivalent of range A1:DQ which is 121 columns)
but if you need more I created a generator in your sheet where you just input number of columns and it will create you the formula you just copy-paste in Conditional formatting:
tho still not truly dynamic solution but hey, better than a nail in the eye

Google Spreadsheet sum which always ends on the cell above

How to create a Google Spreadsheet sum() which always ends on the cell above, even when new cells are added? I have several such calculations to make on each single column so solutions like this won't help.
Example:
On column B, I have several dynamic ranges which has to be summed. B1..B9 should be summed on B10, and B11..B19 should be summed on B20. I have tens such calculations to make. Every now and then, I add rows below the last summed row , and I want them to be added to the sum. I add a new row (call it 9.1) before row 10, and a new raw (let's call it 19.1) before row 20. I want B10 to contain the sum of B1 through B9.1 and B20 to contain the sum of B11:B19.1.
On excel, I have the offset function which does it like charm. But how to do it with google spreadsheet? I tried to use formulas like this:
=SUM(B1:INDIRECT(address(row()-1,column(),false))) # Formula on B10
=SUM(B11:INDIRECT(address(row()-1,column(),false))) # Formula on B20
But on Google Spreadsheet, all it gives is a #name error.
I wasted hours trying to find a solution, maybe someone can calp?
Please advise
Amnon
You are probably looking for formula like:
=SUM(INDIRECT("B1:"&ADDRESS(ROW()-1,COLUMN(),4)))
Google Spreadsheet INDIRECT returns reference to a cell or area, while - from what I recall - Excel INDIRECT returns always reference to a cell.
Given Google's INDIRECT indeed has some hard time when you try to use it inside SUM as cell reference, what you want is to feed SUM with whole range to be summed up in e.g. a1 notation: "B1:BX".
You get the address you want in the same way as in EXCEL (note "4" here for row/column relative, by default Google INDIRECT returns absolute):
ADDRESS(ROW()-1,COLUMN(),4)
and than use it to prepare range string for SUM function by concatenating with starting cell.
"B1:"&
and wrap it up with INDIRECT, which will return area to be sum up.
REFERRING TO BELOW ANSWER from Druvision (I cant comment yet, I didn't want to multiply answers)
Instead of time consuming formulas corrections each time row is inserted/deleted to make all look like:
=SUM(INDIRECT(ADDRESS(ROW()-9,COLUMN(),4)&":"&ADDRESS(ROW()-1,COLUMN(),4)))
You can spare one column in separate sheet for holding variables (let's name it "def"), let's say Z, to define starting points e.g.
in Z1 write "B1"
in Z2 write "B11"
etc.
and than use it as variable in your sum by using INDEX:
SUM(INDIRECT(INDEX(def!Z:Z,1,1)&":"&ADDRESS(ROW()-1,COLUMN(),4))) - sums from B1 to calculated row, since in Z1 we have "B1" ( the 1,1 in INDEX(...,1,1) )
SUM(INDIRECT(INDEX(def!Z:Z,2,1)&":"&ADDRESS(ROW()-1,COLUMN(),4))) - sums from B11 to calculated row, since in Z2 we have "B11" ( the 2,1 in INDEX(...,2,1) )
please note:
Separate sheet named 'def' - you don't want row insert/delete influence that data, thus keep it on side. Useful for adding some validation lists, other stuff you need in your formulas.
"Z:Z" notation - whole column. You said you had a lot of such formulas ;)
Thus you preserve flexibility of defining starting cell for each of your formulas, which is not influenced by calculation sheet changes.
By the way, wouldn't it be easier to write custom function/script summing up all rows above cell? If you feel like javascripting, from what I recall, google spreadsheet has now nice script editor. You can make a function called e.g. sumRowsAboveMe() and than just use it in your sheet like =sumRowsAboveMe() in sheet cell.
Note: you might have to replace commas by semicolons
NOTE
After testing this answer, it will only work if the sum is in a different column due to a circular dependency error. Otherwise, the solution is valid.
It's a bit of algebra, but we can take advantage of Spreadsheets' lower right corner drag.
=SUM(X:X) - SUM(X2:X)
Where X is the column you are working with and X2 is your ending point. Drag the formula down and Sheets will increment the X2, thus changing the ending point.
*You mentioned that you had tens of such calculations to make. So in order to fit your exact need, we would subtract your last summation to get that "middle" range that we wanted.
e.g.
B1..B9 should be summed on B10, and B11..B19 should be summed on B20
Because of the circular dependency error mentioned earlier, I can't solve it exactly and put the sum on the same line, but this could work in other cases where the sum needs to be stored in a different column.
=SUM(B:B) - SUM(B9:B) //Formula on C10 (Sum of B1..B9)
=SUM(B:B) - SUM(B19:B) - B10 // Formula on C20 (Sum of B11..B19)
This is based on #PsychoFish, here is the solution:
=SUM(INDIRECT(SUBSTITUTE(ADDRESS(1,COLUMN(),4),"1","")&"3:"&ADDRESS(ROW()-1,COLUMN(),4)))
Simply replace the "3:" for the row to start sum.
#PsychoFish is correct but cannot be dragged and copied since the column is literal and hard coded, and #Druvision was in the right direction but was wrong... basically ended up with the same issue of having to re-enter the ranges and then sliding the formulas over and over.
You guys are making this harder than you have to. I just leave a couple of empty rows above by "sum" row (you can format them to be filled with color or something to keep them from being inadvertently used), then just add your new rows just above those special rows.
Agree with what user7255446 said that everyone is overcomplicating. Keep one row blank before your sum row. And then whenever you want to insert a new row, click on your blank row and use "Insert row ABOVE" instead of "insert row below". Your sum formula will automatically adjust.
Example: I want to sum from B1 to B19. I leave row 20 blank. In cell B21, put =SUM(B1:B20). Then if you ever need to insert a new row, click on row 20 and choose "Insert row above". The sum formula automatically changes to =SUM(B1:B21) for you. And of course your sum cell is now B22.
General syntax:
=SUM(INDIRECT(cell_reference_as_string1 &":"& cell_reference_as_string2)
with for example:
cell_reference_as_string1 = ADDRESS(ROW(),COLUMN(),4)
cell_reference_as_string2 = ADDRESS(ROW()-1,COLUMN(),4)
I like how #abernier describes the general solution. So far only alphabet-based A1 notation (A being first column, 1 being first row) are being used. It keeps confusing me, especially when thinking of number of columns left of another column. I like the number-based R1C1 notation much better. To use R1C1 notation for INDIRECT, you need to pass FALSE like so:
=SUM(INDIRECT("R1C"&COLUMN()&":R"&(ROW()-1)&"C"&COLUMN(), FALSE))
I hope you find that helpful, too.
OFFSET() can be used/abused for this purpose. Give it the absolute address of the top left of the range, 0 and 0 for the row/column offsets, and the height/width of the range. Let OFFSET() be the argument to SUM(), SUMIF(), etc.
ROW() and COLUMN() are handy when computing the desired height/width. Be sure to remember to subtract one to exclude the current row/column, or else you're liable to end up with a circular reference. If you have header rows/columns, subtract for them too.
For example, to sum everything from A2 down, excluding the current row, try:
=SUM(OFFSET($A$2,0,0,ROW()-2,1))
To sum everything to the left of the current cell, wherever it may be, try:
=SUM(OFFSET(INDIRECT("RC1",FALSE),0,0,1,COLUMN()-1))
Now let's flip things upside down, to show that this works in the other direction. Suppose you want to sum the B column, starting below the current row, until (and including) row #10. Try this:
=SUM(OFFSET($B$10,ROW()-9,0,10-ROW(),1))
You can avoid negative offsets, while still summing column B:
=SUM(OFFSET(INDIRECT("RC2",FALSE),1,0,10-ROW(),1))
Remove the "2" to instead sum the current column:
=SUM(OFFSET(INDIRECT("RC",FALSE),1,0,10-ROW(),1))
(Credit to Tom Sharpe, who commented above.) INDEX() can be used in a range expression. You might prefer this over OFFSET(), so I'm putting it here. The following sums everything from G1 down to the row above the current:
=SUM(G1:INDEX(G:G,ROW()-1))
Here's how I do it.
This formula does not require you to edit or enter anything about the particular column you would like to sum
=SUM(INDIRECT(CONCATENATE(address(1,column(),4),":",LEFT(address(1,column(),4),1))&ROW()-1))
The answer by #PsychoFish led me in the correct way.
The only issue that I had to rewrite the formula again from each column and each sum. So here is the improved formula, which sums the previous 9 cells on the same column, without hardcoding the column or row numbers:
=SUM(INDIRECT(ADDRESS(ROW()-9,COLUMN(),4)&":"&ADDRESS(ROW()-1,COLUMN(),4)))
The only issue is that I had to rewrite the formulas if someone adds or deletes a row. In this case I should change 9 to 10 or 8 corrspondingly.

Resources