Nic*_*k P 4 javascript asynchronous synchronous synchronize
我正在开发一个需要获取一些数据并处理它的javascript项目,但我遇到了JavaScript异步性质的问题.我想要做的是如下所示.
//The set of functions that I want to call in order
function getData() {
//gets the data
}
function parseData() {
//does some stuff with the data
}
function validate() {
//validates the data
}
//The function that orchestrates these calls
function runner() {
getData();
parseData();
validate();
}
Run Code Online (Sandbox Code Playgroud)
在这里,我希望每个函数在继续下一次调用之前等待完成,因为我遇到程序在检索之前尝试验证数据的情况.但是,我还希望能够从这些函数返回一个值进行测试,所以我不能让这些函数返回一个布尔值来检查完成.在进入下一个调用之前,如何让javascript等待函数运行完成?
使用承诺:
//The set of functions that I want to call in order
function getData(initialData) {
//gets the data
return new Promise(function (resolve, reject) {
resolve('Hello World!')
})
}
function parseData(dataFromGetDataFunction) {
//does some stuff with the data
return new Promise(function (resolve, reject) {
resolve('Hello World!')
})
}
function validate(dataFromParseDataFunction) {
//validates the data
return new Promise(function (resolve, reject) {
resolve('Hello World!')
})
}
//The function that orchestrates these calls
function runner(initialData) {
return getData(initialData)
.then(parseData)
.then(validate)
}
runner('Hello World!').then(function (dataFromValidateFunction) {
console.log(dataFromValidateFunction);
})Run Code Online (Sandbox Code Playgroud)
它们不仅容易掌握,而且从代码可读性的角度来看也很有意义.在这里阅读更多相关信息.如果您在浏览器环境中,我建议使用此 polyfill.
您引用的代码将同步运行。JavaScript 函数调用是同步的。
所以我会认为getData,parseData和/或validate涉及异步操作(如在浏览器中,或使用AJAXreadFile中的NodeJS)。如果是这样,您基本上有两个选项,这两个选项都涉及callbacks。
第一个是让这些函数接受它们在完成时调用的回调,例如:
function getData(callback) {
someAsyncOperation(function() {
// Async is done now, call the callback with the data
callback(/*...some data...*/);
});
}
Run Code Online (Sandbox Code Playgroud)
你会像这样使用它:
getData(function(data) {
// Got the data, do the next thing
});
Run Code Online (Sandbox Code Playgroud)
回调的问题在于它们很难组合并且具有相当脆弱的语义。所以发明了promise来给它们更好的语义。在 ES2015(又名“ES6”)或一个像样的承诺库中,它看起来像这样:
function getData(callback) {
return someAsyncOperation();
}
Run Code Online (Sandbox Code Playgroud)
或者如果someAsyncOperation未启用承诺,则:
function getData(callback) {
return new Promise(function(resolve, reject) {
someAsyncOperation(function() {
// Async is done now, call the callback with the data
resolve(/*...some data...*/);
// Or if it failed, call `reject` instead
});
});
}
Run Code Online (Sandbox Code Playgroud)
似乎对你没有多大作用,但关键之一是可组合性;你的最终函数看起来像这样:
function runner() {
return getData()
.then(parseData) // Yes, there really aren't () on parseData...
.then(validate); // ...or validate
}
Run Code Online (Sandbox Code Playgroud)
用法:
runner()
.then(function(result) {
// It worked, use the result
})
.catch(function(error) {
// It failed
});
Run Code Online (Sandbox Code Playgroud)
这是一个例子;它只能在支持PromiseES2015 和 ES2015 箭头函数的相当新的浏览器上工作,因为我很懒惰,用箭头函数编写它并且没有包含 Promise 库:
function getData(callback) {
someAsyncOperation(function() {
// Async is done now, call the callback with the data
callback(/*...some data...*/);
});
}
Run Code Online (Sandbox Code Playgroud)
getData(function(data) {
// Got the data, do the next thing
});
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
15466 次 |
| 最近记录: |