我要发布下面的全部代码。
我正在使用Google脚本,从不断变化的工作表中提取一些数据,执行计算,然后重新填充工作表。
正在将数据调用到应用程序中,因此我正在尝试尽快进行计算(因此,如果有人可以告诉我更有效的方法来执行此操作,这也将有所帮助)。
当我尝试调用conda
函数或invoicePrice()
函数时,我收到TypeError:函数找不到。
tiers()
答案 0 :(得分:2)
问题
从另一个函数(invoicePrice
调用时,正确声明的函数(calcsOnColumns2
)是undefined
。
复制步骤
想象一下,您有三个名为A
,B
,C
的函数,然后调用B
会导致错误:
function A() {
var A = 0;
return [A];
}
function C() {
var a = A();
var A = a[0];
}
function B() {
A();
C();
}
您可能已经注意到这是您的功能归根结底-行为是由于起重:
B
调用A
,该函数返回第一个元素为Array
的{{1}}; 0
调用函数C
并覆盖A
到A
的输出; 相反,在第二步中,A
被声明为等于A
的第一个元素,然后才调用a
。由于A
是从对a
的调用中获取其值的,因此A
将是A
,结果是:undefined
->“不是函数” < / p>
优化
[undefined]()
,getRange()
)放入循环中-除非输入/输出总是很慢,所以通常最好将所有内容加载到内存中并进行处理那里的数据。getValue()
内声明两个同名的变量,将其移到外部作用域)。 我对您的脚本进行了一些优化,看看(请在使用前检查一下,因为我们没有示例数据,所以我无法对其进行测试)。您还可以做更多的事情(尤其是关于if...else
中的循环),但这应该是一个开始:
calcsOnColumns2
注释
/**
* [Your decription here]
* @returns {Number[]}
*/
function invoicePrice() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var subtotalDisplaySheet = ss.getSheetByName('SubtotalDisplay');
// define row to do calculations on
var AVals = subtotalDisplaySheet.getRange("A1:A1000").getValues();
var ALast = AVals.filter(String).length;
// Set order No. here
var orderNoPrev = subtotalDisplaySheet.getRange(ALast - 1, 3).getValue();
var orderNo = subtotalDisplaySheet.getRange(ALast, 3).setValue(orderNoPrev + 1);
// invoicePrice the total number of items
var itemRange = subtotalDisplaySheet.getRange(ALast, 4, 1, 14).getValues()[0];
// set the values of the constants on the Products page
var productsSheet = ss.getSheetByName("Products");
var priceRange = productsSheet.getRange("F1:F1000").getValues();
var pLast = priceRange.filter(String).length;
var pGrab = priceRange.splice(0, pLast);
var outputInvoicePrice = 0;
var weightRange = productsSheet.getRange("V1:V1000").getValues();
var wLast = weightRange.filter(String).length;
var wGrab = weightRange.splice(0, wLast);
var orderAmounts = subtotalDisplaySheet.getRange(Alast, 17).getValues();
var total = 0;
for (var i = 0, len = 13; i <= len; i++) {
var nextI = i + 1;
var orderAmount = orderAmounts[0][i + 4];
total += orderAmount;
var perKGInvoice = pGrab[nextI].map(Number);
var weights = wGrab[nextI].map(Number);
var casePrice = perKGInvoice * weights;
outputInvoicePrice += orderAmount * casePrice;
}
Logger.log(outputInvoicePrice, ALast, pGrab, wGrab);
return [outputInvoicePrice, ALast, pGrab, wGrab];
}
/**
* Gets values from 5 rows in
* a column starting from row 3
* @param {Sheet} sheet
* @param {Number} column
* @returns {*[]}
*/
function getGridValues(sheet, column) {
var range = sheet.getRange(3, column, 5, 1);
return range
.getValues()
.map(function (row) {
return row[0];
});
}
/**
* [Your decription here]
* @returns {Number[]}
*/
function tiers() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var discountGridSheet = ss.getSheetByName("DiscountGrid");
var invoicePriceCall = invoicePrice();
var outputInvoicePrice = invoicePriceCall[0];
var ALast = invoicePriceCall[1];
var beefDiscount = 0;
var sfDiscount = 0;
var currentTier = "";
var tierValues = getGridValues(discountGridSheet, 3);
var tier1 = tierValues[0];
var tier2 = tierValues[1];
var tier3 = tierValues[2];
var tier4 = tierValues[3];
var tier5 = tierValues[4];
var minNotmet = discountGridSheet.getRange(10, 3).getValue();
var tierBeefDiscountValues = getGridValues(discountGridSheet, 4);
var tier1BeefDiscount = tierBeefDiscountValues[0];
var tier2BeefDiscount = tierBeefDiscountValues[1];
var tier3BeefDiscount = tierBeefDiscountValues[2];
var tier4BeefDiscount = tierBeefDiscountValues[3];
var tier5BeefDiscount = tierBeefDiscountValues[4];
var tierSfDiscountValues = getGridValues(discountGridSheet, 5);
var tier1SfDiscount = tierSfDiscountValues[0];
var tier2SfDiscount = tierSfDiscountValues[1];
var tier3SfDiscount = tierSfDiscountValues[2];
var tier4SfDiscount = tierSfDiscountValues[3];
var tier5SfDiscount = tierSfDiscountValues[4];
if (outputInvoicePrice < tier1) {
beefDiscount = tier1BeefDiscount;
sfDiscount = tier1SfDiscount;
currentTier = "Minimum Not Met";
}
else if (outputInvoicePrice < tier2) {
beefDiscount = tier1BeefDiscount;
sfDiscount = tier1SfDiscount;
currentTier = "Tier 1";
}
else if (outputInvoicePrice < tier3) {
beefDiscount = tier2BeefDiscount;
sfDiscount = tier2SfDiscount;
currentTier = "Tier 2";
}
else if (outputInvoicePrice < tier4) {
beefDiscount = tier3BeefDiscount;
sfDiscount = tier3SfDiscount;
currentTier = "Tier 3";
}
else if (outputInvoicePrice < tier5) {
beefDiscount = tier4BeefDiscount;
sfDiscount = tier4SfDiscount;
currentTier = "Tier 4";
}
else {
beefDiscount = tier5BeefDiscount;
sfDiscount = tier5SfDiscount;
currentTier = "Tier 5";
}
var subtotalDisplaySheet = ss.getSheetByName("SubtotalDisplay");
var subtotalDisplayRange = subtotalDisplaySheet.getRange(ALast, 20, 3, 1);
subtotalDisplayRange.setValues([
[beefDiscount],
[sfDiscount],
[currentTier]
]);
return [beefDiscount, sfDiscount, tier1];
}
/**
* Foramts amount string
* @param {Number} amount
* @returns {Function}
*/
function formatAmount(amount) {
return function (discount, caseOrder) {
return amount + " cases @" + discount.toFixed(2) + "/kg = ~$" + caseOrder.toFixed(2);
};
}
/**
* Counts sum by discount, amount and weights
* @param {Number} amount
* @param {Number} weights
* @returns {Number}
*/
function countSum(amount, weights) {
return function (discount) {
return discount * amount * weights;
};
}
/**
* Counts discount case per Kg
* @param {Number} perKG
* @returns {Number}
*/
function countDiscountCase(perKG) {
return function (discount) {
return perKG - (perKG * discount);
};
}
/**
* [Your decription here]
*/
function calcsOnColumns2() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var subtotalDisplaySheet = ss.getSheetByName("SubtotalDisplay");
var invoicePriceCall = invoicePrice();
var outputInvoicePrice = invoicePriceCall[0];
var ALast = invoicePriceCall[1];
var priceRange = invoicePriceCall[2];
var weightRange = invoicePriceCall[3];
var tiers = tiers();
var beefDiscount = tiers[0];
var sfDiscount = tiers[1];
var tier1 = tiers[2];
var beefSum = 0;
var sfSum = 0;
var orderAmounts = subtotalDisplaySheet.getRange(ALast, 17).getValues();
for (var i = 0, len = 13; i <= len; i++) {
var orderAmount = orderAmounts[0][i + 4];
var nextI = i + 1;
var perKGInvoice = priceRange[nextI].map(Number);
var weights = weightRange[nextI].map(Number);
var casePrice = perKGInvoice * weights;
var subtotalRange = subtotalDisplaySheet.getRange(ALast, i + 32);
var formatAmountOrder = formatAmount(orderAmount);
var countDisountSum = countSum(orderAmount, weights);
var countPerKGCase = countDiscountCase(perKGInvoice);
// Split up seafood and beef with if statement:
if (i < 9) {
var discountCaseBeef = countPerKGCase(beefDiscount);
var beefCaseOrder = countDisountSum(discountCaseBeef);
beefSum += beefCaseOrder;
} else {
var discountCaseSF = countPerKGCase(sfDiscount);
var sfCaseOrder = countDisountSum(discountCaseSF);
sfSum += sfCaseOrder;
}
if (orderAmount) {
subtotalRange.setValue(
i < 9 ?
formatAmountOrder(discountCaseBeef, beefCaseOrder) :
formatAmountOrder(discountCaseSF, sfCaseOrder)
);
}
if (i == len) {
subtotalDisplaySheet.getRange(ALast, 24).setValue(beefSum);
subtotalDisplaySheet.getRange(ALast, 25).setValue(sfSum);
// if statement to go here if min order size not met
var subtotalRange = subtotalDisplaySheet.getRange(ALast, 27);
var sumOfSums = beefSum + sfSum;
subtotalRange.setValue(sumOfSums > tier1 ? "Minimum order size not met" : sumOfSums);
var totalDiscount = outputInvoicePrice - sumOfSums;
subtotalDisplaySheet.getRange(ALast, 29).setValue(totalDiscount);
subtotalDisplaySheet.getRange(ALast, 30).setValue(outputInvoicePrice);
}
}
}
是一个示例,但是功能样式会
说甚至是有问题的。)i++
invoicePrice
说得更多)。参考