Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/445.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript Google脚本中的全局变量(电子表格)_Javascript_Variables_Google Apps Script_Global - Fatal编程技术网

Javascript Google脚本中的全局变量(电子表格)

Javascript Google脚本中的全局变量(电子表格),javascript,variables,google-apps-script,global,Javascript,Variables,Google Apps Script,Global,我一直在尝试在GoogleApps脚本(在电子表格中)中使用一些函数来修改全局变量,但我似乎无法理解 基本上,我想声明一个变量(在本例中为“globalTestVar”),并且每次两个函数(GlobalArtestFunctionOne和two)中的一个启动时,该变量都应该递增一 问题是,每次按下按钮时都会再次声明变量,即使if(typeof(globalTestVar)==“undefined”)-语句应该处理这个问题 我已经习惯了Objective C和Java,我可以在开始时声明变量,并在

我一直在尝试在GoogleApps脚本(在电子表格中)中使用一些函数来修改全局变量,但我似乎无法理解

基本上,我想声明一个变量(在本例中为“globalTestVar”),并且每次两个函数(GlobalArtestFunctionOne和two)中的一个启动时,该变量都应该递增一

问题是,每次按下按钮时都会再次声明变量,即使if(typeof(globalTestVar)==“undefined”)-语句应该处理这个问题

我已经习惯了Objective C和Java,我可以在开始时声明变量,并在代码中的任何地方修改这些变量

如果这是一个基本的问题,我很抱歉,但我已经在谷歌上搜索了好几个小时,我就是无法让它工作

代码如下:

logstuff("outside");


function logstuff(logInput){
var sheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName('Sheet1');
var lastRow = sheet.getLastRow() + 1;
sheet.getRange("A"+lastRow).setValue(logInput);
return;
}


if (typeof(globalTestVar) == 'undefined') {
logstuff('declaring global variable');
globalTestVar = 0;

} else {
logstuff('global variable has been declared'); 
}



function globalVarTestUIFunction() {
var app = UiApp.createApplication().setTitle('Test UI');
var doc = SpreadsheetApp.getActive();
var formPanel = app.createVerticalPanel();


var buttonF1 = app.createButton('F1');
var buttonbuttonF1ClickHandler = app.createServerClickHandler("globalVarTestFunctionOne");
buttonF1.addClickHandler(buttonbuttonF1ClickHandler);
buttonbuttonF1ClickHandler.addCallbackElement(formPanel);

var buttonF2 = app.createButton('F2');
var buttonbuttonF2ClickHandler = app.createServerClickHandler("globalVarTestFunctionTwo");
buttonF2.addClickHandler(buttonbuttonF2ClickHandler);
buttonbuttonF2ClickHandler.addCallbackElement(formPanel);


app.add(formPanel);

formPanel.add(buttonF1);
formPanel.add(buttonF2);


doc.show(app);

return app;
}



function globalVarTestFunctionOne() {
logstuff('globalVarTestFunctionOne');
globalTestVar++;
logstuff('Value of globalTestVar: ' + globalTestVar);
}

function globalVarTestFunctionTwo() {
logstuff('globalVarTestFunctionTwo');
globalTestVar++;
logstuff('Value of globalTestVar: ' + globalTestVar);
}
输出:

  • 外部3
  • 声明全局变量
  • 外部3
  • 声明全局变量
  • 全动脉功能酮
  • globalTestVar的值:1
  • 外部3
  • 声明全局变量
  • 全球动脉功能二
  • globalTestVar的值:1
我已经编写了自己的函数“logstuff”来打印消息,因为我不喜欢内置的Logger.log-function


谢谢大家!

您不会喜欢这样:GAS中的全局变量是静态的-您不能更新它们并期望它们保留其值。一、 同样,谷歌搜索了几个小时

您可以使用
CacheService
ScriptDB
作为此类问题的可能存储
CacheService
快速且易于使用,但受到限制,因为缓存最终将过期。我还没有尝试ScriptDB

PropertiesService->Properties 目前(2015年),我认为应该使用类和返回类型

关于全球范围
据我所知,每次对脚本函数的新调用(时间触发器、用户单击菜单项、按下按钮等)都将导致对脚本进行新的完整解析,而不会记忆以前的执行情况,除非它们以某种方式被持久化(例如,在电子表格范围内或使用
属性
).

尽管CacheService可以工作,但它的最长使用寿命为6小时。 这可以通过使用PropertiesService来解决,如@consideRatio所述

示例包装器可能是(将变量注入全局上下文)

注册Globals.init后,变量可以像普通变量一样使用。不过,这适用于原语,因为复杂对象不支持观察程序,所以必须在脚本端或显式刷新它们

/* In case you need to start over */
function restart_simulations() {
  Globals.reset('counter');
  Globals.reset('state');
  
  test_run();
}

function test_run() {
  /* After running init once, you can use global var as simple variable */
  Globals.init('counter', 1); // Required to use "counter" var directly, as simple variable
  
  /* Complex objects are also accepted */
  Globals.init('state', { logined: false, items: [] }); 
  
  /* Using primitives is simple */
  Logger.log('Counter was ' + counter);
  counter = counter + 1;
  Logger.log('Counter is now ' + counter);

  /* Let's modify complex object */
  Logger.log('State was ' + JSON.stringify(state));
  
  state.items.push(state.logined ? 'foo' : 'bar');
  state.logined = ! state.logined;
  
  Logger.log('State is now ' + JSON.stringify(state));
  
  /* Unfortunately, watchers aren't supported. Non-primitives have to be flushed */
  /* Either explicitly */
  //Globals.save('state');  
  
  /* Or all-at-once, e.g. on script end */
  Globals.flush();  
}
以下是在不同的3次跑步中保留的内容

First run:

[20-10-29 06:13:17:463 EET] Counter was 1
[20-10-29 06:13:17:518 EET] Counter is now 2
[20-10-29 06:13:17:520 EET] State was {"logined":false,"items":[]}
[20-10-29 06:13:17:523 EET] State is now {"logined":true,"items":["bar"]}

Second run:

[20-10-29 06:13:43:162 EET] Counter was 2
[20-10-29 06:13:43:215 EET] Counter is now 3
[20-10-29 06:13:43:217 EET] State was {"logined":true,"items":["bar"]}
[20-10-29 06:13:43:218 EET] State is now {"logined":false,"items":["bar","foo"]}

Third run:

[20-10-29 06:14:22:817 EET] Counter was 3
[20-10-29 06:14:22:951 EET] Counter is now 4
[20-10-29 06:14:22:953 EET] State was {"logined":false,"items":["bar","foo"]}
[20-10-29 06:14:22:956 EET] State is now {"logined":true,"items":["bar","foo","bar"]}
您可以在这里查看工作示例


好吧,这太令人不安了。必须有一种使用某种全局变量的方法。我考虑了一种变通方法,使用“变量”表来保存/修改和获取全局变量。但这不是很优雅,也不是很有效。我使用了
CacheService
来做我需要的事情,但那是短期存储以提高性能。您可能会发现
ScriptDB
更好,但我没有尝试过。是的,cacheService对字符串和数字很有效,但是可以使用cacheService存储数组吗?否-您不能在缓存中存储数组,更糟糕的是:
JSON.stringify()
似乎不会返回JSON字符串,也不会报告错误。不过,您可以将数组存储在ScriptDB中。这是否比将它们存储为表中的范围更好取决于您对它们所做的操作。全局变量不是静态的,它们是全局的,指的是它们的作用域。在执行上下文中,全局变量可用于所有代码块。当您按下客户端脚本(UiApp、HtmlService)中的按钮时,将创建一个新的服务器端上下文以运行相应的处理程序,并且该新上下文具有一组唯一的“全局”变量。严格地说,您的变量没有被“重新声明”,与“未定义”的比较只意味着它没有在此上下文中赋值。
First run:

[20-10-29 06:13:17:463 EET] Counter was 1
[20-10-29 06:13:17:518 EET] Counter is now 2
[20-10-29 06:13:17:520 EET] State was {"logined":false,"items":[]}
[20-10-29 06:13:17:523 EET] State is now {"logined":true,"items":["bar"]}

Second run:

[20-10-29 06:13:43:162 EET] Counter was 2
[20-10-29 06:13:43:215 EET] Counter is now 3
[20-10-29 06:13:43:217 EET] State was {"logined":true,"items":["bar"]}
[20-10-29 06:13:43:218 EET] State is now {"logined":false,"items":["bar","foo"]}

Third run:

[20-10-29 06:14:22:817 EET] Counter was 3
[20-10-29 06:14:22:951 EET] Counter is now 4
[20-10-29 06:14:22:953 EET] State was {"logined":false,"items":["bar","foo"]}
[20-10-29 06:14:22:956 EET] State is now {"logined":true,"items":["bar","foo","bar"]}