I have a Google Sheet problem that looks like this:
Google Sheet Image Example
In Column "A" I have a group of IDs organized in a specific way.
In Column "B" I have a list with all the IDs present in column "A" and their specific audience name. The names and IDs are separated by ";" and the ID is the number between "( )".
I need a formula or solution that replaces the ID on column "A" with the audience name referenced on column "B".
Here's a link to the example sheet: https://docs.google.com/spreadsheets/d/1BS6_frcliNV882kWcDb2ZjpjERdPtI_ZiivWzHvRVuk/edit?usp=sharing
In your situation, for example, how about using Google Apps Script? I thought that when Goolgle Apps Script is used, your goal might be able to be achieved using a simple script. The sample script is as follows.
Sample script:
Please copy and paste the following script to the script editor of Google Spreadsheet. And, please put a custom function of =SAMPLE(A2:B). By this, the script is run.
function SAMPLE(values) {
const obj = values.flatMap(([, b]) => [...b.matchAll(/(.+?) \((.+?)\);?/g)].map(e => [e[2].trim(), e[1].trim()]));
return values.map(([a]) => obj.reduce((s, e) => s.replace(...e), a));
}
Testing:
When this script is run to your provided Spreadsheet, the following result is obtained.
Note:
This sample script can be used for your provided Spreadsheet. When you change the structure of each value, this script might not be able to be used. Please be careful about this.
References:
Custom Functions in Google Sheets
map()
reduce()
Related
I'm trying add easy updating prices into a google sheet.
I need the market price from
//*[#id="app"]/div/section[2]/section/div[1]/section[3]/div/section[1]/ul/li[1]/span[2]
https://www.tcgplayer.com/product/242811/pokemon-celebrations-celebrations-elite-trainer-box?Language=English
I need it to display just the one number from the XPath to a cell, and I can't seem to figure out where I am going wrong. I've been using the IMPORTXML function and it won't return a value.
=IMPORTXML(A2,"//*[#id='app']/div/section[2]/section/div[1]/section[3]/div/section[1]/ul/li[1]/span[2]")
where A2 is the URL.
In your situation, it seems that the value of the market price cannot be directly retrieved from the URL of https://www.tcgplayer.com/product/242811/pokemon-celebrations-celebrations-elite-trainer-box?Language=English. But, fortunately, it seems that that value can be directly retrieved from the endpoint of API. So, how about the following sample formula?
Sample formula:
=REGEXEXTRACT(JOIN(",",IMPORTDATA(A1)),"marketPrice:(.+?),")*1
or
=REGEXEXTRACT(QUERY(TRANSPOSE(IMPORTDATA(A1)),"WHERE Col1 matches 'marketPrice.+'"),"marketPrice:(.+)")*1
The cell "A1" has the URL of https://mpapi.tcgplayer.com/v2/product/242811/details.
In the case of https://www.tcgplayer.com/product/242811/pokemon-celebrations-celebrations-elite-trainer-box?Language=English, please use 242811 from the URL to the endpoint of API like https://mpapi.tcgplayer.com/v2/product/242811/details.
Result:
Note:
The value from the URL is JSON data. In this case, the following custom function can be also used. In this case, please copy and paste the following script to the script editor of Spreadsheet and save the script. And please put a custom function of =SAMPLE("url") to a cell.
const SAMPLE = url => JSON.parse(UrlFetchApp.fetch(url).getContentText()).marketPrice;
References:
IMPORTDATA
REGEXEXTRACT
Custom Functions in Google Sheets
it's not possible to scrape JS content into google sheets:
I'm trying to modify this formula to automatically provide the definition in Column B when a word is entered in Column A. Currently, the formula looks like this...
=(index(split(concatenate(importxml("https://www.merriam-webster.com/dictionary/"&$A2,"//span[#class='dtText']")),": ",FALSE,TRUE),1,1))
This works, but it doesn't automatically provide the definition when adding new words. I tried modifying the formula using an arrayformula (seen below), but it repeats the definition for the word in A2.
={"Definition";arrayformula(if(A2:A="",,index(split(concatenate(importxml("https://www.merriam-webster.com/dictionary/"&$A2:A,"//span[#class='dtText']")),": ",FALSE,TRUE),1,1)))}
Any ideas on how to fix this? Thanks for your help. Here's the link to the Google Sheet below so you can edit it.
https://docs.google.com/spreadsheets/d/1_OrJwlOHxVXZBKA0GFaiXnRS1x5OCszrR9m3UlMuWRY/edit?usp=sharing
Thanks for your help!
According to this similar article about Use importXML from column of URLs with arrayformula returning same duplicated result in google sheet:
unfortunately, that won't do because ARRAYFORMULA does not support IMOPRTXML formulas. you could try to look up some scripted workaround for this task or give up on one cell solution
Alternative Solution
Perhaps you can use this sample onEdit(e) simple trigger script below instead via Apps Script that is bound to your Spreadsheet file:
Follow this guide on how to add the script as a bound script in your Spreadsheet file:
Sample Script:
function onEdit(e){
var sh = e.range.getSheet();
if(e.range.getColumn() != 1 || e.range.getRow() == 1) return; //ignore if you have not put the word on column A or Col #1 & on row 1
sh.getRange("B"+e.range.getRow()).setFormula("=(index(split(concatenate(importxml(\"https://www.merriam-webster.com/dictionary/"+e.range.getValue()+"\",\"//span[#class='dtText']\")),\": \",FALSE,TRUE),1,1))");
if(e.range.getValue() == "") sh.getRange("B"+e.range.getRow()).clear(); //clear column B row if the adjacent word on column A gets deleted
}
Sample Demonstration
Input the words crystal & believe on cells A2 & A3
I've created a spreadsheets consist of multiple complex dates & strings.
When I use concatenate, the date become numbers
=CONCATENATE('2021'!A2:'2021'!F61)
The results is like
44519in44471out44472Guest1in44475out44476SGuest2
How can I produce the result like this in one cell
November 2021
in 6/11 out 10/11 Guest 1
in 26/11 out 28/11 Guest 2
December 2021
in 29/12 out 31/12 Guest 3
I just need the copy & paste cell features, but I can't find any.
An option would be to use an Apps Script Custom Function.
First, open a bound script by selecting Tools > Script editor, and copy the following function to the script:
function CONCAT_WITH_DATES(rangeNotation) {
const values = SpreadsheetApp.getActiveSheet()
.getRange(rangeNotation)
.getDisplayValues()
.map(row => row.filter(cell => String(cell)))
.map(row => row.join(" "))
.join("\n");
return values;
}
Once the script is saved, you can use this function the same you would use any sheets built-in function:
Note:
The input range has to be provided in quotes in order to retrieve the values with the displayed format via Range.getDisplayValues(). If the range is provided directly, the date values won't keep the format.
Reference:
Custom Functions in Google Sheets
Please note that an extra column F, which should be blank, is selected in order to identity row break
=REGEXREPLACE(REGEXREPLACE(REGEXREPLACE(TEXTJOIN("♦",FALSE,'2021'!A1:F5),"♦{2,}",CHAR(10)),"♦$",),"♦",CHAR(9))
I'm working with google forms and google sheets. I'm trying to create a summary sheet that will automatically update as the form is being filled.
I've been able to pull the data from the other sheets using a FILTER function. Now I want to add a column that shows the name of a country to the filtered column. I tried using concatenate but it didn't work as well as I'd hoped. Can someone help me figure out how to solve this problem.
Please see here for an example of the problem.
Well this is a very inelegant brute force way, but I think it works. See Solution-GK in your sheet.
=QUERY({
{TRANSPOSE(SPLIT(REPT("Nigeria~",ROWS(UNIQUE(FILTER(NIGERIA!A:E,NIGERIA!C:C<TODAY(),NIGERIA!B:B="Charity Fundraiser")))),"~")),
UNIQUE(FILTER(NIGERIA!A:E,NIGERIA!C:C<TODAY(),NIGERIA!B:B="Charity Fundraiser"))};
{TRANSPOSE(SPLIT(REPT("Sierra Leone~",ROWS(UNIQUE(FILTER('SIERRA LEONE'!A:E,'SIERRA LEONE'!C:C<TODAY(),'SIERRA LEONE'!B:B="Charity Fundraiser")))),"~")),
UNIQUE(FILTER('SIERRA LEONE'!A:E,'SIERRA LEONE'!C:C<TODAY(),'SIERRA LEONE'!B:B="Charity Fundraiser"))}},
"select Col1,Col2,Col3,Col4, Col5 where Col2 is not null")
I've added a hard coded literal of the country name, repeated it the number of times needed for the matching data rows, and made it into the first column in your existing data array. I repeat this for the second array you have for the second country.
I'm sure there are far more elegant ways to do this, so we'll see what else is proposed. If you had a list somewhere in your sheet of your country names - ie. Nigeria and Sierra Leone, possibly many more - I'm sure an elegant solution would cycle through those names, pulling the name to build the concatenated data ranges, and also adding the name as the text for each row.
Without needing a list in the sheet, a little bit of code could find all of your tab names, and exclude the non data ones, eg. Solution Here and Summary, and process all of the rest as data.
Note: I'm not clear that you need your UNIQUE statements, unless you are expecting duplicates for some reason. Also, the outer QUERY doesn't seem to be necessary - the inner FILTERs seem to do everything you need.
You could do this with an Apps Script Custom Function.
First, open a bound script by selecting Tools > Script editor, and copy the following functions to the script (check inline comments for more details about the code):
// Copyright 2020 Google LLC.
// SPDX-License-Identifier: Apache-2.0
function SUMMARIZE_FUNDRAISING_EVENTS(sheetNames, ...ranges) {
const ss = SpreadsheetApp.getActiveSpreadsheet();
sheetNames = sheetNames.split(","); // Comma-separated string to array of sheet names
const filteredData = sheetNames.map(sheetName => { // Iterate through each sheet name
const sheet = ss.getSheetByName(sheetName);
if (sheet) { // Check if sheet exists with this name
const sheetData = sheet.getRange(2,1,sheet.getLastRow()-1,4).getValues(); // Source sheet data
const filteredData = sheetData.filter(rowData => {
return rowData[1] === "Charity Fundraiser" && rowData[2] < new Date()
}); // Filter data according to date and type of event
filteredData.forEach(filteredRow => filteredRow.unshift(sheetName)); // Add sheet name to filtered data
return filteredData;
}
}).flat();
return filteredData;
}
Once it is defined, you can use the function SUMMARIZE_FUNDRAISING_EVENTS the same you would any sheets built-in function. This function would accept a series of parameters:
A comma-separated string with the names of the sheets whose data should be summarized (don't add blank spaces after the comma or similar).
The different source ranges (in your case, NIGERIA!A:E and 'SIERRA LEONE'!A:E).
Both of these are necessary, because, on the one side, specifying the source ranges as parameters makes sure that the function executes and updates the summarized data every time the source ranges are edited, and on the other side, when passed as parameters, these source ranges don't contain information about the sheet names, which the script will need when returning the summarized data.
Example of calling the function:
Reference:
Custom Functions in Google Sheets
Google Sheets script for if/then statement
Can someone help me write a script for the following:
I need my Google Sheet to input "No" in column W if column J has the word "transfer" in it. Otherwise, it needs to input "N/A".
I currently have the following formula in my Google spreadsheet:
=IF(ISERROR(SEARCH("transfer",J2,1)),"N/A","No")
but as you know, the formula is cleared out once it gets a new entry from the linked Google form.
Any help would be tremendously appreciated.
This might restore your formula. Try attaching it to the form submit trigger.
function fallingFromTheSky(e)
{
var row=e.range.getRow();
e.range.getSheet().getRange(row,23).setFormula('=IF(ISERROR(SEARCH("transfer",J'+ row +',1)),"N/A","No")');
}