I am building a Google sheet that references data from a source sheet where columns and rows may shift, and values may even change. Because shifting can occur, an ID system has been implemented. Here is a very simplified version:
In my own sheet, the goal is to pull in values and place them based on the corresponding ID. Currently, to pull this off, I am using the IMPORTRANGE function with a FILTER to get the desired value, based on the ID in the column. So to find and place the value "United States" underneath ID 1, I use the following:
=FILTER(IMPORTRANGE("doc_url", "Sheet1!A1:A5"),IMPORTRANGE("doc_url", "Sheet1!B1:B5")=A1)
I am aware it's not super great to use IMPORTRANGE on a cell-by-cell basis, as it becomes quite intensive with heavy usage (and the actual sheet I am building has many more values to pull). I feel like there must be a more efficient way to pull and arrange these values by the correct ID, but I haven't been able to figure it out so far.
Is it possible to build a function that would pull the full range in the order I am expecting all in one go?
Example Source Sheet
Example Target Sheet
try in A2:
=INDEX(IFNA(HLOOKUP(A1:E1,
TRANSPOSE(QUERY(IMPORTRANGE("doc_url", "Sheet1!A1:B5"),
"select Col2,Col1", )), 2, 0)))
Related
Is there a formula that will allow me to use a range of sheet ids to stack import ranges from multiple sheets?
Example
=importrange(A2:A,"Sheet1!A:F") in the example is meant to be illustrative of what I'm trying to achieve.
I'm aware I can use
={IMPORTRANGE("id1","Sheet1!A:F");IMPORTRANGE("id2","Sheet1!A:F"); IMPORTRANGE("id3","Sheet1!A:F")}
however, what I'm hoping to achieve is a growing list of ids in column A that when a new id is entered (and after creating a method for allowing permissions) will add on and expand the stack of importranges.
The closest I got was this but I'm getting a space on either side of the id and wasn't able to progress from there.
not possible to accomplish directly. the best you can do is to use a formula to generate formula:
=INDEX({""; "={"&TEXTJOIN("; ", 1, "IMPORTRANGE("""&
FILTER(A2:A, A2:A<>"")&""", ""Sheet1!A:F"")")&"}"})
I have a Google Sheet that has a main master sheet, with a column for users to fill in their Name to show they are "working" on that row, then that row gets populated to their own tab based on a =QUERY(Master!A3:AA,"select * Where L='Name'") for each of the users' tabs, there is 8 total tabs where users are updating information. This is already quite a bit of processing on Googles part, so I am trying to generate a separate Google Sheet that pulls in the information that the users are entering on each of their tabs so the management can monitor that sheet for updates and then both sheets will run a lot faster/smoother.
I have tried using a VLookup with this syntax: =vlookup(A3,importrange("sheetID",{"Name1!$A$3:$N";"Name2!$A$3:$N";"Name3!$A$3:$N";"Name4!$A$3:$N";"Name5!$A$3:$N";"Name6!$A$3:$N";"Name7!$A$3:$N";"Name8!$A$3:$N"}),12,FALSE) which gives me an #N/A Error, cannot find Value '1' in VLOOKUP evaluation.
I have also tried using a =QUERY({importrange("sheetID"x8 with the ranges)}, "Select Col12,Col13,Col14 where Col2 matches '^.\*($" &B3 & ").\*$'")
That only returns headers, I am trying to get the query to basically find the unique key in Column A then spit out what is in Col 12-14, but that doesn't seem to work either. Columns 1-11 are static, but Columns 12-14 are what I am trying to populate for the management, which is the work that the staff is inputting on each of their tabs.
I can get the query working if I keep it on the same worksheet as the one the staff is working on, but then it bogs down the whole sheet so I would like to keep it separate if possible. Any ideas? I can't provide a sample sheet at this time since it has financial info on it, but I can add more details if I know what to look for.
your formula should be:
=VLOOKUP(A3, {
IMPORTRANGE("sheetID1", "Name1!A3:N");
IMPORTRANGE("sheetID2", "Name2!A3:N");
IMPORTRANGE("sheetID3", "Name3!A3:N");
IMPORTRANGE("sheetID4", "Name4!A3:N");
IMPORTRANGE("sheetID5", "Name5!A3:N");
IMPORTRANGE("sheetID6", "Name6!A3:N");
IMPORTRANGE("sheetID7", "Name7!A3:N");
IMPORTRANGE("sheetID8", "Name8!A3:N")}, 12, 0)
keep in mind that every importrange needs to be run as a standalone formula where you connect your sheets by allowing access. only then you can use the above formula
Below is a sample of the Google Sheet I'm working on:
https://docs.google.com/spreadsheets/d/1LDsfn_FMdUSfuFZAyuXf5gdlOSN9yLqhT1RY8aX7Nfs/edit?usp=sharing
On the spreadsheet Team Totals, I'm trying to calculate all the sales based on the date, the type of sale, and the program type starting from Row 27.
The problem I have run into is that the Named Range, Consultants, only pulls the data from the first cell of the Named range (Octo). What I want is for a formula that will pull the data of the selected range from each entry in the named range and sum them together.
For reference, I put what the proper values should be starting from Row 33.
The closest example I have seen was from this website: https://www.got-it.ai/solutions/excel-chat/excel-tutorial/sumif/sumif-across-multiple-sheets
However, I get the same problem that only the first cell in the named range gets pulled.
I feel like I'm missing something simple, but I have been bouncing it around my head for hours and can't figure it out. Any help is greatly appreciated.
So after trying to figure out a way not to use an iterative process, I folded and did this:
=arrayformula(SUMIFS(INDIRECT("'"&$B$4&"'!F6:F100"),INDIRECT("'"&$B$4&"'!D6:D100"),$B$2,INDIRECT("'"&$B$4&"'!E6:E100"),E$27,INDIRECT("'"&$B$4&"'!A6:A100"),$A41)+
SUMIFS(INDIRECT("'"&$B$5&"'!F6:F100"),INDIRECT("'"&$B$5&"'!D6:D100"),$B$2,INDIRECT("'"&$B$5&"'!E6:E100"),E$27,INDIRECT("'"&$B$5&"'!A6:A100"),$A41)+
SUMIFS(INDIRECT("'"&$B$6&"'!F6:F100"),INDIRECT("'"&$B$6&"'!D6:D100"),$B$2,INDIRECT("'"&$B$6&"'!E6:E100"),E$27,INDIRECT("'"&$B$6&"'!A6:A100"),$A41)+
SUMIFS(INDIRECT("'"&$B$7&"'!F6:F100"),INDIRECT("'"&$B$7&"'!D6:D100"),$B$2,INDIRECT("'"&$B$7&"'!E6:E100"),E$27,INDIRECT("'"&$B$7&"'!A6:A100"),$A41)+
SUMIFS(INDIRECT("'"&$B$8&"'!F6:F100"),INDIRECT("'"&$B$8&"'!D6:D100"),$B$2,INDIRECT("'"&$B$8&"'!E6:E100"),E$27,INDIRECT("'"&$B$8&"'!A6:A100"),$A41)+
SUMIFS(INDIRECT("'"&$B$9&"'!F6:F100"),INDIRECT("'"&$B$9&"'!D6:D100"),$B$2,INDIRECT("'"&$B$9&"'!E6:E100"),E$27,INDIRECT("'"&$B$9&"'!A6:A100"),$A41))
This formula allows me to cut and paste it to various cells easily, and does the job I need it to, while still using the indirect reference so I can change names without breaking the formula (granted I change the worksheet name as well).
I will need to edit this to include all possible worksheet amounts I can forsee, but once it's done, I won't have to tinker with names anymore.
I'm not happy with this answer, as it creates a really long and ugly formula, essentially repeating the same formula 20 times, but it does work. I feel like there should be an easy function that would be able to do this.
This will return Total sales:
=if(isna(ArrayFormula(QUERY({Lo!$A$5:$F; Tulio!$A$5:$F;Ya!$A$5:$F; Miguel!$A$5:$F;Kevin!$A$5:$F; Octo!$A$5:$F}, "select sum(Col6) where Col1=date '"&TEXT(A28,"yyyy-mm-dd")&"' label sum(Col6) ''",0)))=TRUE,0,ArrayFormula(QUERY({Lo!$A$5:$F; Tulio!$A$5:$F;Ya!$A$5:$F; Miguel!$A$5:$F;Kevin!$A$5:$F; Octo!$A$5:$F}, "select sum(Col6) where Col1=date '"&TEXT(A28,"yyyy-mm-dd")&"' label sum(Col6) ''",0)))
BTW, I get Total sales of $0, $615.50 and $2,498.00
The best way to pull data from a lot of unknown tab names without a script is to actually CREATE the tab names beforehand. On your sheet it looks like you're anticipating/making space for 21 employees. If I were you, I would just create 15 more tabs named Temp7,Temp8,Temp9... etc. Then you can just "hide" those tabs. Then a formula can be built in your totals section that will easily stack all the tabs up using an array literal and a QUERY( { } ) to add up the totals for you without all this INDIRECT() nonsense that you have been going through to pull from the individual tab names.
Would pre-adding tab names be something you were interested in if I could show you the formulas to make the totals easy to calculate?
In column B are listed IDs of Google Sheets. In column C are listed cells, from which I want to import data.
Screenshot of the table
In column D is shown the result of using IMPORTRANGE() by simply dragging it. e.g. for D1 it looks like:
=IMPORTRANGE(B1;C1)
for D2:
=IMPORTRANGE(B2;C2)
and so on.
In column E I want to display the same result but using ARRAYFORMULA that looks like:
=ARRAYFORMULA(IMPORTRANGE(B2:B4,C2:C4))
but the function displays only the data from the first spreadsheet.
People complain about this permissions issue a lot, but it's not hard to solve. What I do is have a sheet which I name "Splash sheet" into which I paste the URLs of the documents I wish to link. To its right is a column headed "permit to connect" which contains IMPORTRANGE formulas importing a single cell from each sheet -- usually a cell containing a confirmation code, number or document name -- on a sheet also named "Splash Sheet." For example,
=IF(B3="enter URL",,CONCATENATE(IMPORTRANGE(B3,"Splash sheet!A1")," ",IMPORTRANGE(B3,"Splash sheet!B1")))
So, when you first connect a spreadsheet via its URL, you get those messages telling you you need to connect, you click the Permit Access, the confirmation code/number/document name appears in the second column, and voilá, your sheets are connected forevermore! Now all your other IMPORTRANGEs referencing that URL will work, and you can use IMPORTRANGE formulas that reference the URL-containing cells on the "splash sheet."
As for the OP's original question, I came here seeking an answer to the same problem, and after more research have realized that we are attempting the impossible here. No way to do this an ARRAYFORMULA. No way around writing formulas that reference every single cell a document's URL may go into.
Problem is you can't make arrays of arrays in spreadsheets; that would involve multiple dimensions, and the medium is inherently two-dimensional. This is what people use databases for.
ARRAYFORMULA doesn't work when importing data (I think it relates to permissions). You could use something like this, =IFERROR(IMPORTRANGE(B5:B7;C5:C7)) and pre-fill the column first, but still there would be the permissions issue. Each new imported sheet needs it's permissions granted by a user.
TLDR: If I understand your intention correctly when you say you would like to see
=ARRAYFORMULA(IMPORTRANGE(B2:B4,C2:C4)), I believe you can make that
happen using the following.
=ARRAYFORMULA(IMPORTRANGE(
INDIRECT(ADDRESS(ROW(B2:B4), COLUMN(B2:B4)),
INDIRECT(ADDRESS(ROW(C2:C4), COLUMN(C2:C4))
)
Breakdown
Use IMPORTRANGE with INDIRECT to create ranges inside ARRAYFORMULA
Call INDIRECT with the ADDRESS function
Call ADDRESS with the ROW and COLUMN functions since they take ranges via ARRAYFORMULA
using IMPORTRANGE with INDIRECT
IMPORTRANGE's two parameters are the spreadsheet url stored in B2:B4 for this example and the range (e.g. sheet!A1:B2) stored in C2:C4.
Since IMPORTRANGE doesn't take a range reference directly as you mentioned, you'll need to build it for each row with ARRAYFORMULA using the INDIRECT function.
INDIRECT can be used to compose a cell reference using A1 notation, for instance
=IMPORTRANGE(INDIRECT("B" & 2), INDIRECT("C" & 2))
will produce the same result as
=IMPORTRANGE(B2, C2)
Since this produces the same result, we now just have to find a way to make INDIRECT work with ARRAYFORMULA
Use ADDRESS to build the parameters for INDIRECT
Next you want to use ADDRESS to build the A1 reference for INDIRECT. For the current purposes, ADDRESS takes a numerical value for row and column as parameters
=INDIRECT(ADDRESS(2,2))
will produce the same result as
=INDIRECT("B" & 2)
Since these two are interchangeable, now we just need to find a way to get the numerical row and column values out of ARRAYFORMULA.
Call ADDRESS using the ROW and COLUMN functions
From there, you can get the row and column indexes from standard A1 notation using the ROW and COLUMN functions. While this may seem like we're pointlessly going in circles, the difference now is that ROW and COLUMN perform as expected with the ranges provided by ARRAYFORMULA. So given that ADDRESS will return $B$2 using using either method below
=ADDRESS(2,2)
or
=ADDRESS(ROW(B2),COLUMN(B2))
we now know that
=ARRAYFORMULA(ADDRESS(ROW(B2:B4),COLUMN(B2:B4)))
will produce the following array of addresses
{ $B$2; $B$3; $B$4 }
Final Assembly
So when we put this all together, we get
=ARRAYFORMULA(IMPORTRANGE(
INDIRECT(ADDRESS(ROW(B2:B4), COLUMN(B2:B4)),
INDIRECT(ADDRESS(ROW(C2:C4), COLUMN(C2:C4))
)
where INDIRECT(ADDRESS(ROW(B2:B4), COLUMN(B2:B4)) is more or less interchangeable with what you might expect from B2:B4 inside ARRAYFORMULA and represents the url parameter
and INDIRECT(ADDRESS(ROW(C2:C4), COLUMN(C2:C4)) is roughly interchangeable with what you might expect from C2:C4 inside ARRAYFORMULA and represents the range parameter.
Suggestions on organization
I recommend using the indentation (Alt +Enter to create a new line ) above along with your indentation of choice to keep it easier to read. In the end it's just a bit more syntactic sugar and if spaces are used well it shouldn't be much harder to understand and make changes to 6 months later.
RE: Permissions - as mentioned by Atiq Zabinski, just placing a simple
IMPORTRANGE("http:/xxxx", "A1") somewhere on the sheet will provide a
means to know if the sheet is connected or not and the error message
should give you a context menu for connecting the sheet. You'll might
want to stay away from error handling in these scenarios as it will
slow down the process of connecting the sheets.
I am reading this.
Is there a way I can select worksheet there, I need to do queries in a specific worksheet.
I tried with Google Spreadsheet API, but answer I am getting is difficult to parse, since fields are calculated by Google and there is no documentation about them.
Workaround
I just moved sheet to the first position and it worked with a query like the one specified in the first link I posted.
Note the first sheet is selected by default and there is no way to select sheet, that, is my question.
Easier than trying luck with a gid number there is the possibilty to pass sheet parameter with sheet name:
https://spreadsheets.google.com/tq?key=0AsD4widwbn0rdE9HM2VwZ1h2UktFUi0xTy1lOVlqblE&sheet=sheet1&tq=select%20A
https://spreadsheets.google.com/tq?key=0AsD4widwbn0rdE9HM2VwZ1h2UktFUi0xTy1lOVlqblE&sheet=sheet2&tq=select%20A
Note the sheet parameter. I could not find source of this again.
Use gid=
like this:
https://spreadsheets.google.com/tq?key=0Ao_WaOWBqWmjdGRZV3dxdW1sdXhaeUs0cko5ZEVldEE&gid=0&tq=select%20A
https://spreadsheets.google.com/tq?key=0Ao_WaOWBqWmjdGRZV3dxdW1sdXhaeUs0cko5ZEVldEE&gid=4&tq=select%20A
Notice that the gid is not the same, and the result is not the same.
Note: gid values start at 0, so sheet1: gid=0, sheet2: gid=1. The gid values never change even if a sheet is deleted/renamed.