Vue official statement:Cn.vuejs.org/v2/guide/re…
The ultimate goal of reactive data is to run functions when the object itself or object properties change, the most common being the Render function.
In terms of implementation, VUE uses several core components:
- Observer
- Dep
- Watcher
- Scheduler
Observer
The objective of the Observer is very simple: to convert an ordinary object into a responsive object
To achieve this, the Observer converts each property of the Object through object.defineProperty to a property with a getter and setter, so that vue has a chance to do something else when the property is accessed or set.
An Observer is an internal vUE constructor that can be used indirectly through a static vUE method called vue.Observable (Object).
In the component lifecycle, this happens after beforeCreate and before Created.
In practice, it will recursively traverse all the attributes of the object to complete the deep attribute conversion.
Since the traversal can only traverse the current properties of an object, it cannot detect the future dynamic addition or deletion of properties. Therefore, VUE provides two instance methods, SET and SET, and SET and DELETE, for developers to add or delete properties to existing reactive objects through these two instance methods.
For an array, VUE changes its implicit stereotype because it needs to listen for methods that might change the contents of the array
- In short, the objective of the Observer is for an object to be perceived by the VUE as reading, assigning, and changing its internal array.
Dep
There are two unsolved problems, namely what to do when a property is read, and what to do when a property changes, and that needs to be solved by Dep.
Dep stands for Dependency.
Vue creates a Dep instance for each property in the responsive object, the object itself, and the array itself. Each Dep instance has the ability to do two things:
- Record dependencies: Who is using me
- Send out updates: I have changed, and I want to inform those who use me
When a property of a reactive object is read, it does dependency collection: someone used me
When you change a property, it sends an update: Listen to those who use me, I’ve changed
Watcher
So here’s another question, how does Dep know who’s using me?
To solve this problem, we need to rely on another thing, Watcher.
When a function executes and uses reactive data, reactive data has no way of knowing which function is using it
So vUE solves this problem in a clever way
Instead of executing the function directly, we hand it over to something called a Watcher, and a Watcher is an object, and every time a function like this is executed, it should create a Watcher and execute it through a Watcher
/ / deP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP); / / DeP (deP) There’s a Watcher that uses my property
When the Dep dispatches an update, it notifies all previously logged Watchers that I have changed
For each vUE component instance, there is at least one Watcher that records the render function of that component.
Watcher will first run the Render function once to collect dependencies, and the responsive data used in render will record the Watcher.
The DEP notifizes the Watcher when the data changes, and Watcher rerun the Render function to re-render the interface and re-record the current dependencies.
Scheduler
This leaves one final problem, which is that if Watcher rerun the corresponding function after Dep notifes watcher, it could cause the function to run frequently, resulting in inefficiency
Imagine a function given to Watcher that uses attributes A, B, c, and D. The a, B, C, and D properties log dependencies, and the following code triggers four updates:
state.a = "new data";
state.b = "new data";
state.c = "new data";
state.d = "new data";
Copy the code
This is obviously not appropriate, so instead of immediately executing the corresponding function when Watcher is notified of the update, it actually hands itself over to something called a scheduler
The scheduler maintains an execution queue that only exists once for the same watcher. Instead of executing the watcher immediately, the scheduler uses a tool method called nextTick to put the executed Watcher into the microqueue of the event loop. The specifics of nextTick are done through Promise
- NextTick is exposed to developers via this.$nextTick
- Specific treatment methods of nextTick are as follows:
- Cn.vuejs.org/v2/guide/re…
- That is, when reactive data changes, the render function executes asynchronously and in microqueues