This article attempts to explain what callbacks are from the perspective of novice asynchronous programming.
Synchronous and asynchronous
Before introducing callback functions, let’s look at two concepts: synchronous and asynchronous.
Synchronous behavior usually refers to code being executed line by line from top to bottom, with subsequent code always executed after the previous code has been executed.
An example of a synchronous operation is as follows:
let a, b;
function foo() {
a = 1;
}
foo();
b = a + 1;
console.log(b); / / 2
Copy the code
Since the code executes sequentially, the function foo() is called first; B = a + 1; , so b = a + 1; The value of a must have been determined to be 1 and can be used immediately, and the final result of variable B is 2.
Asynchronous behavior means that code is not executed sequentially, and subsequent code may not always be executed after previous code has been executed.
Examples of asynchronous operations are as follows:
let a, b;
function foo() {
a = 1;
}
setTimeout(foo, 1000); // Call foo() after 1 second
b = a + 1;
console.log(b); //NaN
Copy the code
Instead of explicitly calling foo(), we pass the function name foo to setTimeout, and the JavaScript runtime will automatically call foo() after 1 second.
First, the code is still executed sequentially, when setTimeout(foo, 1000); When the JavaScript main thread realizes that this is a task to be executed asynchronously, it will queue foo() and proceed with the following synchronization code b = a + 1; , when b = a + 1; After execution, all synchronized code is executed, and the JavaScript main thread then fetchs the required task from the task queue to execute, i.e., foo() is executed one second later.
Because b is equal to a plus 1; Executed before foo(), so variable B ends up with NaN after this asynchronous operation.
The callback function
Having introduced the concepts of synchronization and asynchrony, let’s take a look at what callbacks are.
In the asynchronous operation example, setTimeout(foo, 1000); Foo in this code can be called a callback function. The callback function is the code that is put into the task queue by the main thread, usually in function units, and is not executed until all synchronized code has been executed.
So the asynchronous example above would have to look like this if it wanted the same result as the synchronous operation:
let a, b;
function foo() {
a = 1;
b = a + 1;
console.log(b); / / 2
}
setTimeout(foo, 1000); // Call foo() after 1 second
Copy the code
Because b depends on A, and A = 1; B = a + 1; b = a + 1; b = a + 1; Also move to the callback function. The code in the callback function is also executed sequentially, so b = a + 1; The statement should be placed at a = 1; After the statement. That would make the variable B equal to 2.
Callback function application
AJAX operations are a very common asynchronous operation scenario in JavaScript programming. If you are not familiar with AJAX concepts, I strongly recommend that you learn them.
Here is an example of sending an AJAX request using jQuery:
function handleSuccess(res) {
console.log(res);
}
function handleError(xhr) {
console.log(xhr.status);
}
$.ajax({
type: 'GET'.url: 'http://localhost:3000/'.success: handleSuccess,
error: handleError
});
Copy the code
Where success registers the successful callback function handleSuccess, error registers the failed callback function handleError.
When the AJAX request succeeds and gets a response, the JavaScript runtime automatically calls handleSuccess or handleError when the request fails.
The purpose of the callback function is to process the result of the request asynchronously. Because sending an AJAX request is a time-consuming operation, it can greatly reduce JavaScript efficiency if handled synchronously. When an AJAX request is made, we don’t know when to get the response, so we use asynchronous programming to register the code that handles the response as a callback function.
As you can see, callbacks and asynchrony go hand in hand. The concept of callbacks only appears in asynchronous programming, and there is no need for callbacks in synchronous programming.
P.S.
The description of JavaScript asynchronous execution mechanism in this paper is not accurate. To understand JavaScript asynchronous execution mechanism, you must learn Event Loop. This article is not intended to introduce too many complex concepts, but to give a quick understanding of what callbacks are for beginners of asynchronous programming.
If you’re a JavaScript developer, that’s the end of this article. If you happen to be a Python developer, you can keep reading.
For those of you who have written Python crawlers, you have probably heard of the well-known crawler framework Scrapy. You may have seen code similar to the following in the spider file for your Scrapy project:
class DoubanSpider(scrapy.Spider) :
name = 'douban'
allowed_domains = ['movie.douban.com']
def start_requests(self) :
for i in range(0.10):
url = f'https://movie.douban.com/top250?start={i * 25}'
yield scrapy.Request(url=url, callback=self.parse)
Copy the code
Callback =self.parse registers self.parse as a callback function. Request does not block, but when the Request succeeds and the response is received, Scrapy automatically calls our registered callback self.parse. This is similar to jQuery’s AJAX.
When programming in Python, you spend most of your time writing synchronous code, so many beginners feel uncomfortable with asynchronous programming for the first time. When you get stuck learning one programming language, you may find inspiration in another.