Ein Artikel, der diesen Punkt versteht und 70 % der Front-End-Leute erreicht
Ein Kollege blieb aufgrund des dadurch angezeigten Bug
-Problems, vue2 hat dieses Zeigeproblem
hängen und die Pfeilfunktion wurde verwendet, was dazu führte, dass der entsprechende props
>. Er wusste es nicht, als ich es ihm vorstellte, und dann habe ich mir bewusst die Front-End-Kommunikationsgruppe angesehen. Bisher können es mindestens 70 % der Front-End-Programmierer nicht verstehen dies code>Weisen Sie darauf hin, wenn Sie nichts gelernt haben, geben Sie mir bitte eine große Klappe. <code>bug
,vue2的this指向问题
,使用了箭头函数,导致拿不到对应的props
。当我给他介绍的时候他竟然不知道,随后也刻意的看了一下前端交流群,至今最起码还有70%以上的前端程序员搞不明白,今天给大家分享一下this
指向,如果啥都没学会,请给我一个大嘴巴子。
1. 调用位置
- 作用域跟在哪里定义有关,与在哪里执行无关
-
this
指向跟在哪里定义无关,跟如何调用,通过什么样的形式调用有关 -
this
(这个) 这个函数如何被调用(方便记忆) - 为了方便理解,默认情况下不开启严格模式
2. 绑定规则
上面我们介绍了,this
的指向主要跟通过什么样的形式调用有关。接下来我就给大家介绍一下调用规则,没有规矩不成方圆,大家把这几种调用规则牢记于心就行了,没有什么难的地方。
- 你必须找到调用位置,然后判断是下面四种的哪一种绑定规则
- 其次你要也要晓得,这四种绑定规则的优先顺序
- 这两点你都知道了 知道this的指向对于你来说 易如反掌
2.1 默认绑定
函数最常用的调用方式,调用函数的类型:独立函数调用
function bar() { console.log(this) // window }
- bar是不带任何修饰符的直接调用 所以为默认绑定 为
window
- 在严格模式下 这里的
this
为undefined
2.2 隐式绑定
用最通俗的话表示就是:对象拥有某个方法,通过这个对象访问方法且直接调用(注:箭头函数特殊,下面会讲解)
const info = { fullName: 'ice', getName: function() { console.log(this.fullName) } } info.getName() // 'ice'
- 这个函数被
info
发起调用,进行了隐式绑定,所以当前的this
为info
,通过this.fullName
毫无疑问的就访问值为ice
隐式丢失 普通
有些情况下会进行隐式丢失,被隐式绑定的函数会丢失绑定对象,也就是说它为变为默认绑定,默认绑定的this
值,为window
还是undefined
取决于您当前所处的环境,是否为严格模式。
const info = { fullName: 'ice', getName: function() { console.log(this.fullName) } } const fn = info.getName fn() //undefined
这种情况下就进行了隐式丢失,丢失了绑定的对象,为什么会产生这样的问题呢?如果熟悉内存的小伙伴,就会很容易理解。
- 这里并没有直接调用,而是通过
info
找到了对应getName
的内存地址,赋值给变量fn
- 然后通过
fn
直接进行了调用 - 其实这里的本质 就是独立函数调用 也就是为
window
,从window
中取出fullName
属性,必定为undefined
隐式丢失 进阶
这里大家首先要理解什么是回调函数。其实可以这样理解,就是我现在不调用它,把他通过参数的形式传入到其他地方,在别的地方调用它。
//申明变量关键字必须为var var fullName = 'panpan' const info = { fullName: 'ice', getName: function() { console.log(this.fullName) } } function bar(fn) { //fn = info.getName fn() // panpan } bar(info.getName)
- 首先
bar
中的fn
为一个回调函数 -
fn = info.getName
参数传递就是一种隐式赋值,其实跟上面的隐式丢失是一个意思,他们都是指向的fn = info.getName
引用,也就是它们的内存地址 - 因为他们的
this
丢失,也就是函数独立调用,默认绑定规则,this
为全局的window
对象 - 注意: 为什么申明必须为
var
呢?- 因为只有
var
申明的变量才会加入到全局window
对象上 - 如果采用
letconst
则不是,具体的后续介绍一下这两个申明变量的关键字
- 因为只有
- 但是有些场景,我不想让隐式丢失怎么办,下面就来给大家介绍一下显示绑定,也就是固定调用。
2.3 显示绑定
但是在某些场景下,this
的改变都是意想不到的,实际上我们无法控制回调函数的执行方式,因此没有办法控制调用位置已得到期望的绑定即this指向。
接下来的显示绑定就可以用来解决这一隐式丢失问题。
2.3.1 call/apply/bind
js中的 ”所有“函数都有一些有用的特性,这个跟它的原型链有关系,后续我会在原型介绍,通过原型链js中变相实现继承的方法,其中call/apply/bind
1. Aufrufort
- Der Bereich hängt davon ab, wo er definiert ist, nicht davon, wo er ausgeführt wird
-
this
zeigt auf eine Funktion, die nichts damit zu tun hat, wo sie definiert ist, sondern wie sie aufgerufen wird und in welcher Form this(this) So wird aufgerufen (leicht zu merken)
- Um das Verständnis zu erleichtern, ist der strikte Modus standardmäßig nicht aktiviert
2. Bindungsregeln
Wie wir oben eingeführt haben, hängt die Ausrichtung vonthis
hauptsächlich mit der Form des Aufrufs zusammen. Als nächstes werde ich Ihnen die Anrufregeln vorstellen. Ohne Regeln ist nichts vollständig. 🎜- Sie müssen den Anrufort finden und dann bestimmen, welche der folgenden vier verbindlichen Regeln
- Zweitens müssen Sie auch die Priorität dieser vier verbindlichen Regeln kennen
- Sie kennen diese beiden Punkte und es fällt Ihnen leicht, die Richtung zu kennen
2.1 Standardbindung
🎜 Die gebräuchlichste Art, eine Funktion aufzurufen, die Art des Funktionsaufrufs: unabhängiger Funktionsaufruf🎜var fullName = 'panpan' const info = { fullName: 'ice', getName: function(age, height) { console.log(this.fullName, age, height) } } function bar(fn) { fn.call(info, 20, 1.88) //ice 20 1.88 } bar(info.getName)
- bar ist ein direkter Aufruf ohne Modifikatoren, daher ist die Standardbindung
window
- Im strikten Modus ist
dies
hierundefiniert
2.2 Implizite Bindung
🎜 In den gängigsten Worten bedeutet dies: Das Objekt hat eine bestimmte Methode, und auf die Methode wird über dieses Objekt zugegriffen und direkt aufgerufen (Hinweis: Pfeilfunktionen sind etwas Besonderes, werde ich erklären unten) 🎜var fullName = 'panpan' const info = { fullName: 'ice', getName: function(age, height) { console.log(this.fullName, age, height) } } function bar(fn) { fn.apply(info, [20, 1.88]) //ice 20 1.88 } bar(info.getName)
- Diese Funktion wird von
info
aufgerufen und implizit gebunden, sodass der aktuellethis
info ist, bis this.fullName
Es besteht kein Zweifel, dass der Zugriffswertice
this
-Wert der Standardbindung, unabhängig davon, ob es sich um window handelt. code> oder <code>undefiniert
hängt von der Umgebung ab, in der Sie sich gerade befinden, und davon, ob es sich um den strikten Modus handelt. 🎜var fullName = 'panpan' const info = { fullName: 'ice', getName: function(age, height) { console.log(this.fullName, age, height) //ice 20 1.88 } } function bar(fn) { let newFn = fn.bind(info, 20) newFn(1.88) } bar(info.getName)
- Hier gibt es keinen direkten Aufruf, aber die Speicheradresse, die
getName
entspricht, wird überinfo
gefunden und der Variablenfn zugewiesen code>
- Dann erfolgte der Aufruf direkt über
fn
- Tatsächlich handelt es sich hier im Wesentlichen um einen unabhängigen Funktionsaufruf, nämlich
window, from fullName
aus code>window
undefiniert
🎜Implizit sein Loss Advanced Hier muss jeder zunächst verstehen, was eine Callback-Funktion ist. Tatsächlich kann es so verstanden werden, das heißt, ich rufe es jetzt nicht auf, sondern übergebe es in Form von Parametern an andere Stellen und rufe es woanders auf. 🎜
function Person(name, age) { this.name = name this.age = age } const p1 = new Person('ice', 20) console.log(p1) // {name:'ice', age:20}
- Zuallererst ist
fn
inbar
eine Callback-Funktion fn = info.getName code> Die Parameterübergabe ist eine Art implizite Zuweisung. Sie hat tatsächlich die gleiche Bedeutung wie der oben genannte implizite Verlust. Sie verweisen alle auf <code>fn = info.getName
-Referenzen, die ihre Speicheradressen sind. li>Da ihrthis
verloren geht, wird die Funktion unabhängig aufgerufen und die Standardbindungsregel lautet, dassthis
das globalewindow ist. code> Objekt
- Hinweis: Warum muss die Deklaration
var
sein?- Weil nur durch
var
deklarierte Variablen zum globalenwindow
-Objekt hinzugefügt werden - Wenn
letconst
wird verwendet > Nein, ich werde die beiden Schlüsselwörter zum Deklarieren von Variablen später im Detail vorstellen.
- Weil nur durch
- Aber in einigen Szenarien möchte ich keinen impliziten Verlust ?Ich werde Ihnen sagen, was als nächstes zu tun ist. Lassen Sie uns die Anzeigebindung einführen, bei der es sich um einen festen Aufruf handelt.
2.3 Anzeigebindung
🎜 Aber in einigen Szenarien istdies
The Änderungen sind unerwartet. Tatsächlich haben wir keine Kontrolle darüber, wie die Rückruffunktion ausgeführt wird, daher gibt es keine Möglichkeit zu kontrollieren, ob der aufrufende Ort die erwartete Bindung erhalten hat, das heißt, dass dies darauf verweist. 🎜🎜Die nächste Anzeigebindung kann verwendet werden, um dieses implizite Verlustproblem zu lösen. 🎜2.3.1 call/apply/bind
🎜 Alle Funktionen in js haben einige nützliche Funktionen, diese ist die gleiche wie die Prototypkette von Rufen Sie sie in Funktionen auf. 🎜2.3.2 call
-
call()
方法使用一个指定的this
值和单独给出的一个或多个参数来调用一个函数。- 第一个参数为固定绑定的
this
对象 - 第二个参数以及二以后的参数,都是作为参数进行传递给所调用的函数
- 第一个参数为固定绑定的
- 备注
- 该方法的语法和作用与
apply()
方法类似,只有一个区别,就是call()
方法接受的是一个参数列表,而apply()
方法接受的是一个包含多个参数的数组。
- 该方法的语法和作用与
var fullName = 'panpan' const info = { fullName: 'ice', getName: function(age, height) { console.log(this.fullName, age, height) } } function bar(fn) { fn.call(info, 20, 1.88) //ice 20 1.88 } bar(info.getName)
2.3.3 apply
- 与
call
的方法类似,只是参数列表有所不同- 参数
-
call
参数为单个传递 -
apply
参数为数组传递
-
- 参数
var fullName = 'panpan' const info = { fullName: 'ice', getName: function(age, height) { console.log(this.fullName, age, height) } } function bar(fn) { fn.apply(info, [20, 1.88]) //ice 20 1.88 } bar(info.getName)
2.3.4 bind
-
bind
与apply/call
之间有所不同,bind
传入this
,则是返回一个this
绑定后的函数,调用返回后的函数,就可以拿到期望的this。 - 参数传递则是
- 调用
bind
时,可以传入参数 - 调用
bind
返回的参数也可以进行传参
- 调用
var fullName = 'panpan' const info = { fullName: 'ice', getName: function(age, height) { console.log(this.fullName, age, height) //ice 20 1.88 } } function bar(fn) { let newFn = fn.bind(info, 20) newFn(1.88) } bar(info.getName)
2.4 new绑定
谈到new
关键字,就不得不谈构造函数,也就是JS中的 "类",后续原型篇章在跟大家继续探讨这个new关键字,首先要明白以下几点,new Fn()
的时候发生了什么,有利于我们理解this
的指向。
创建了一个空对象
将this指向所创建出来的对象
把这个对象的[[prototype]] 指向了构造函数的prototype属性
执行代码块代码
如果没有明确返回一个非空对象,那么返回的对象就是这个创建出来的对象
function Person(name, age) { this.name = name this.age = age } const p1 = new Person('ice', 20) console.log(p1) // {name:'ice', age:20}
- 当我调用
new Person()
的时候,那个this所指向的其实就是p1
对象
3. 绑定优先级
3.1 隐式绑定 > 默认绑定
function bar() { console.log(this) //info } const info = { bar: bar } info.bar()
- 虽然这边比较有些勉强,有些开发者会认为这是默认绑定的规则不能直接的显示谁的优先级高
- 但是从另外一个角度来看,隐式绑定,的this丢失以后this才会指向
widonw或者undefined
,变相的可以认为隐式绑定 > 默认绑定
3.2 显示绑定 > 隐式绑定
var fullName = 'global ice' const info = { fullName: 'ice', getName: function() { console.log(this.fullName) } } info.getName.call(this) //global ice info.getName.apply(this) //global ice info.getName.bind(this)() //global ice
- 通过隐式绑定和显示绑定的一起使用很明显 显示绑定 > 隐式绑定
3.3 bind(硬绑定) > apply/call
function bar() { console.log(this) //123 } const newFn = bar.bind(123) newFn.call(456)
3.4 new绑定 > bind绑定
首先我们来说一下,为什么是和bind
比较,而不能对call
和apply
比较,思考下面代码
const info = { height: 1.88 } function Person(name, age) { this.name = name this.age = age } const p1 = new Person.call('ice', 20) //报错: Uncaught TypeError: Person.call is not a constructor
new绑定和bind绑定比较
const info = { height: 1.88 } function Person(name, age) { this.name = name this.age = age } const hasBindPerson = Person.bind(info) const p1 = new hasBindPerson('ice', 20) console.log(info) //{height: 1.88}
- 我们通过
bind
对Person
进行了一次劫持,硬绑定了this为info
对象 -
new
返回的固定this的函数 - 但是我们发现 并不能干预this的指向
3.5 总结
new关键字
> bind
> apply/call
> 隐式绑定
> 默认绑定
4. 箭头函数 (arrow function)
首先箭头函数是ES6
新增的语法
const foo = () => {}
4.1 箭头函数this
var fullName = 'global ice' const info = { fullName: 'ice', getName: () => { console.log(this.fullName) } } info.getName() //global ice
- 你会神奇的发现? 为什么不是默认绑定,打印结果为
ice
- 其实这是
ES6
的新特性,箭头函数不绑定this
,它的this
是上一层作用域,上一层作用域为window
- 所以打印的结果是
global ice
4.2 箭头函数的应用场景 进阶
- 需求: 在
getObjName
通过this
拿到info
中的fullName
(值为ice
的fullName
)
const info = { fullName: 'ice', getName: function() { let _this = this return { fullName: 'panpan', getObjName: function() { console.log(this) // obj console.log(_this.fullName) } } } } const obj = info.getName() obj.getObjName()
当我调用
info.getName()
返回了一个新对象当我调用返回对象的
getObjName
方法时,我想拿到最外层的fullName
,我通过,getObjName
的this访问,拿到的this却是obj
,不是我想要的结果我需要在调用
info.getName()
把this保存下来,info.getName()
是通过隐式调用,所以它内部的this就是info对象getObjName
是obj对象,因为也是隐式绑定,this必定是obj对象,绕了一大圈我只是想拿到上层作用域的this而已,恰好箭头函数解决了这一问题
const info = { fullName: 'ice', getName: function() { return { fullName: 'panpan', getObjName: () => { console.log(this.fullName) } } } } const obj = info.getName() obj.getObjName()
5. 总结
5.1 this的四种绑定规则
默认绑定
隐式绑定
显示绑定 apply/call/bind(也称硬绑定)
new绑定
5.2 this的优先级 从高到低
new绑定
bind
call/apply
隐式绑定
默认绑定
6. 结语
当一切都看起来不起作用的时候,我就会像个石匠一样去敲打石头,可能敲100次,石头没有任何反应,但是101次,石头可能就会裂为两半 我知道并不是第101次起了作用,而是前面积累所致。
大家有疑惑可以在评论区留言 第一时间为大家解答。
(学习视频分享:web前端开发)

Heiße KI -Werkzeuge

Undresser.AI Undress
KI-gestützte App zum Erstellen realistischer Aktfotos

AI Clothes Remover
Online-KI-Tool zum Entfernen von Kleidung aus Fotos.

Undress AI Tool
Ausziehbilder kostenlos

Clothoff.io
KI-Kleiderentferner

AI Hentai Generator
Erstellen Sie kostenlos Ai Hentai.

Heißer Artikel

Heiße Werkzeuge

Notepad++7.3.1
Einfach zu bedienender und kostenloser Code-Editor

SublimeText3 chinesische Version
Chinesische Version, sehr einfach zu bedienen

Senden Sie Studio 13.0.1
Leistungsstarke integrierte PHP-Entwicklungsumgebung

Dreamweaver CS6
Visuelle Webentwicklungstools

SublimeText3 Mac-Version
Codebearbeitungssoftware auf Gottesniveau (SublimeText3)

Heiße Themen



So implementieren Sie mit WebSocket und JavaScript ein Online-Spracherkennungssystem. Einführung: Mit der kontinuierlichen Weiterentwicklung der Technologie ist die Spracherkennungstechnologie zu einem wichtigen Bestandteil des Bereichs der künstlichen Intelligenz geworden. Das auf WebSocket und JavaScript basierende Online-Spracherkennungssystem zeichnet sich durch geringe Latenz, Echtzeit und plattformübergreifende Eigenschaften aus und hat sich zu einer weit verbreiteten Lösung entwickelt. In diesem Artikel wird erläutert, wie Sie mit WebSocket und JavaScript ein Online-Spracherkennungssystem implementieren.

WebSocket und JavaScript: Schlüsseltechnologien zur Realisierung von Echtzeit-Überwachungssystemen Einführung: Mit der rasanten Entwicklung der Internet-Technologie wurden Echtzeit-Überwachungssysteme in verschiedenen Bereichen weit verbreitet eingesetzt. Eine der Schlüsseltechnologien zur Erzielung einer Echtzeitüberwachung ist die Kombination von WebSocket und JavaScript. In diesem Artikel wird die Anwendung von WebSocket und JavaScript in Echtzeitüberwachungssystemen vorgestellt, Codebeispiele gegeben und deren Implementierungsprinzipien ausführlich erläutert. 1. WebSocket-Technologie

So implementieren Sie ein Online-Reservierungssystem mit WebSocket und JavaScript. Im heutigen digitalen Zeitalter müssen immer mehr Unternehmen und Dienste Online-Reservierungsfunktionen bereitstellen. Es ist von entscheidender Bedeutung, ein effizientes Online-Reservierungssystem in Echtzeit zu implementieren. In diesem Artikel wird erläutert, wie Sie mit WebSocket und JavaScript ein Online-Reservierungssystem implementieren, und es werden spezifische Codebeispiele bereitgestellt. 1. Was ist WebSocket? WebSocket ist eine Vollduplex-Methode für eine einzelne TCP-Verbindung.

Einführung in die Verwendung von JavaScript und WebSocket zur Implementierung eines Online-Bestellsystems in Echtzeit: Mit der Popularität des Internets und dem Fortschritt der Technologie haben immer mehr Restaurants damit begonnen, Online-Bestelldienste anzubieten. Um ein Echtzeit-Online-Bestellsystem zu implementieren, können wir JavaScript und WebSocket-Technologie verwenden. WebSocket ist ein Vollduplex-Kommunikationsprotokoll, das auf dem TCP-Protokoll basiert und eine bidirektionale Kommunikation zwischen Client und Server in Echtzeit realisieren kann. Im Echtzeit-Online-Bestellsystem, wenn der Benutzer Gerichte auswählt und eine Bestellung aufgibt

JavaScript und WebSocket: Aufbau eines effizienten Echtzeit-Wettervorhersagesystems Einführung: Heutzutage ist die Genauigkeit von Wettervorhersagen für das tägliche Leben und die Entscheidungsfindung von großer Bedeutung. Mit der Weiterentwicklung der Technologie können wir genauere und zuverlässigere Wettervorhersagen liefern, indem wir Wetterdaten in Echtzeit erhalten. In diesem Artikel erfahren Sie, wie Sie mit JavaScript und WebSocket-Technologie ein effizientes Echtzeit-Wettervorhersagesystem aufbauen. In diesem Artikel wird der Implementierungsprozess anhand spezifischer Codebeispiele demonstriert. Wir

JavaScript-Tutorial: So erhalten Sie HTTP-Statuscode. Es sind spezifische Codebeispiele erforderlich. Vorwort: Bei der Webentwicklung ist häufig die Dateninteraktion mit dem Server erforderlich. Bei der Kommunikation mit dem Server müssen wir häufig den zurückgegebenen HTTP-Statuscode abrufen, um festzustellen, ob der Vorgang erfolgreich ist, und die entsprechende Verarbeitung basierend auf verschiedenen Statuscodes durchführen. In diesem Artikel erfahren Sie, wie Sie mit JavaScript HTTP-Statuscodes abrufen und einige praktische Codebeispiele bereitstellen. Verwenden von XMLHttpRequest

Verwendung: In JavaScript wird die Methode insertBefore() verwendet, um einen neuen Knoten in den DOM-Baum einzufügen. Diese Methode erfordert zwei Parameter: den neuen Knoten, der eingefügt werden soll, und den Referenzknoten (d. h. den Knoten, an dem der neue Knoten eingefügt wird).

Einführung in die Methode zum Abrufen des HTTP-Statuscodes in JavaScript: Bei der Front-End-Entwicklung müssen wir uns häufig mit der Interaktion mit der Back-End-Schnittstelle befassen, und der HTTP-Statuscode ist ein sehr wichtiger Teil davon. Das Verstehen und Abrufen von HTTP-Statuscodes hilft uns, die von der Schnittstelle zurückgegebenen Daten besser zu verarbeiten. In diesem Artikel wird erläutert, wie Sie mithilfe von JavaScript HTTP-Statuscodes erhalten, und es werden spezifische Codebeispiele bereitgestellt. 1. Was ist ein HTTP-Statuscode? HTTP-Statuscode bedeutet, dass der Dienst den Dienst anfordert, wenn er eine Anfrage an den Server initiiert