React类的自定义原型方法中的this指向为什么是undefined?如何解决?(绑定 this 的几种方式)

news/2024/7/24 6:17:17 标签: React, this

首先来看下类中定义的原型方法的this不同调用时的指向:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
</head>
<body>
    <script type="text/javascript">
        class Person{
            constructor(){
                console.log("Person类constructor中的this:");
                console.log(this);
            }

            speak(){
                console.log("Person类speak方法中的this:");
                console.log(this);
            }
        }

        const person1 = new Person(); // this:Person{}
        person1.speak(); // this:Person{}
        const s = person1.speak;
        s(); // this: undefined
        // 此处如果window.s()会报s不存在
    </script>
</body>
</html>

事件调用方法时方法中的this指向:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
</head>
<body>
    <Button onclick="hanleClick()">this指向</Button>
    <script type="text/javascript">
        function hanleClick(){
            console.log("this指向:");
            console.log(this);
        }

        // 当点击Button时,hanleClick中的this指向为window
    </script>
</body>
</html>

类中的方法默认开启了局部的严格模式,严格模式下this为undefined: 

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Document</title>
</head>
<body>
    <Button onclick="hanleClick()">this指向</Button>
    <script type="text/javascript">
        function hanleClick(){
            "use strict"
            console.log("this指向:");
            console.log(this);
        }

        // 开启严格模式前:当点击Button时,hanleClick中的this指向为window
        // 开启严格模式后:当点击Button时,hanleClick中的this指向为undefined
    </script>
</body>
</html>
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <script src="https://unpkg.com/react@16/umd/react.development.js" crossorigin></script>
    <script src="https://unpkg.com/react-dom@16/umd/react-dom.development.js" crossorigin></script>
    <script src="https://unpkg.com/babel-standalone@6/babel.min.js"></script>
    <title>Document</title>
</head>
<body>
    <div id="app"></div>
    <script type="text/babel">
        class MyComponent extends React.Component{
            // 1、handleClick放在哪?MyComponent原型上,供MyComponent实例调用;
            // 2、handleClick是作为onClick的回调,所以不是通过实例调用的,是直接调用;
            // 3、类中的方法默认开启了局部的严格模式,严格模式下this为undefined(这个和Babel没关系)
            handleClick(){
                console.log("React类的自定义方法中的this为:");
                console.log(this); // 当点击h2标签时,this为undefined
            }

            render(){
                return <h2 onClick={this.handleClick}>我是类定义的组件</h2>;
            }
        }

        ReactDOM.render(<MyComponent/>, document.getElementById("app"));
    </script>
</body>
</html>

如何让自定义原型方法中的this指向为组件实例?

 一、在constructor中bind绑定组件的this

class Button extends React.Component{
  constructor(pops){
    super();
    this.handleClick = this.handleClick.bind(this); // 将原型方法handleClick的this指向为实例对象,然后赋给实例方法handleClick,此时实例上和原型上都有handleClick方法
  }

  handleClick = () => {
    console.log("this is ", this);
  }

  render(){
    return (<button onClick={this.handleClick}>按钮</button>)
  }
}

二、方法使用时绑定 this

class Button extends React.Component{
  constructor(props){
    super(props);
  }

  handleClick = () => {
    console.log("this is ", this);
  }

  render(){
    return (<button onClick={this.handleClick.bind(this)}>按钮</button>)
  }
}

ReactDOM.render(
  <Button/>,
  document.getElementById("app")
);

三、使用属性初始化语法:

class LoggingButton extends React.Component {
  // 这个语法确保了 `this` 绑定在  handleClick 中
  // 这里只是一个测试
  handleClick = () => {
    console.log('this is:', this);
  }
 
  render() {
    return (
      <button onClick={this.handleClick}>
        Click me
      </button>
    );
  }
}

四、在回调函数中使用 箭头函数:

class LoggingButton extends React.Component {
  handleClick() {
    console.log('this is:', this);
  }
 
  render() {
    //  这个语法确保了 `this` 绑定在  handleClick 中
    return (
      <button onClick={(e) => this.handleClick(e)}>
        Click me
      </button>
    );
  }
}

五、函数传参:

<button onClick={this.函数名.bind(this, '我是参数')}>点我传递实参</button>
fune(x, e){
    ...
}

...


render(){
    return (<button onClick={e => {this.fune("我是实参", e)}}>点我传递实参</button>)
}

 


http://www.niftyadmin.cn/n/886773.html

相关文章

React中数据子传父的实现

原理&#xff1a;通过props将父组件中的方法传给子组件实现。 父组件&#xff1a; class Parent extends React.Component{constructor(){super();this.state{count: 0}}increase(e){this.setState({count: this.state.counte})}render(){return (<div><p onClick{…

什么是Library

在计算机科学中&#xff0c;library是计算机程序经常用于软件开发的非易失性资源的集合。这些可能包括配置数据&#xff0c;文档&#xff0c;帮助数据&#xff0c;消息模板&#xff0c;预编写的代码和子例程&#xff0c;类&#xff0c;值或类型规范。在IBM OS / 360及其后续版本…

webpack4:基本使用

webpack是基于Node构建&#xff0c;所以wepack支持所有Node API和语法。 即&#xff1a;Chrome浏览器能支持的ECMAScript语法&#xff08;排除DOM、BOM&#xff09;&#xff0c;wbpack都能支持。Chrome不支持ES6&#xff0c;所以webpack也不支持。 创建基本的webpack4.x项目&…

Kubernetes和Docker

定义上的区别 官方定义1&#xff1a;Docker是一个开源的应用容器引擎&#xff0c;开发者可以打包他们的应用及依赖到一个可移植的容器中&#xff0c;发布到流行的Linux机器上&#xff0c;也可实现虚拟化。 官方定义2&#xff1a;k8s是一个开源的容器集群管理系统&#xff0c;…

RAM,ROM,内存还有硬盘的区别

内存&#xff0c;RAM&#xff0c;ROM&#xff0c;CACHE 内存在电脑中起着举足轻重的作用。内存一般采用半导体存储单元&#xff0c;包括随机存储器&#xff08;RAM&#xff09;&#xff0c;只读存储器&#xff08;ROM&#xff09;&#xff0c;以及高速缓存&#xff08;CACHE&a…

云服务器ECS

云服务器ECS&#xff08;Elastic Compute Service&#xff09;是阿里云提供的性能卓越、稳定可靠、弹性扩展的IaaS&#xff08;Infrastructure as a Service&#xff09;级别云计算服务。云服务器ECS免去了您采购IT硬件的前期准备&#xff0c;让您像使用水、电、天然气等公共资…

如何写makefile文件(1)

概述 makefile关系到了整个工程的编译规则。一个工程中的源文件不计数&#xff0c;其按类型、功能、模块分别放在若干个目录中&#xff0c;makefile定义了一系列的规则来指定&#xff0c;哪些文件需要先编译&#xff0c;哪些文件需要后编译&#xff0c;哪些文件需要重新编译&a…

webpack4:实时打包之webpack-dev-server

1、安装&#xff1a; cnpm i webpack-dev-server -D 2、package.json中配置命令&#xff1a; "dev": "webpack-dev-server --open chrome --port 3000 --hot --host 127.0.0.1" {"name": "wp4-1","version": "1.0.…