React DAY03

复习:
1.React是一个用于构建用户界面的JS库;不涉及HTML/CSS;Facebook于2013开源,最新版本V18.2
2.使用React的两种方式:
①脚本引入式: react.js / react-dom.js / babel.js
②脚手架方式: npx create-react-app 项目名
3.JSX
JavaScript XML,是使用类似XML的语法创建虚拟DOM对象,本身是TypeScript语法一部分。
所有的JSX都会被Babel编译为: “use strict”; React.createElement(‘button/BuyCount’,…)
4.JSX中的数据绑定
内容绑定:<div>{表达式}</div>
属性绑定:<img src={表达式}/>
样式绑定:<div className={表达式} style={表达式}>
事件绑定:<button onClick={函数} onmouseenter={函数}>
双向数据绑定:
条件渲染:
列表渲染:
5.创建自定义组件的两种语法:
①函数式组件 —— 面向过程的编程思想©

function BuyCount( props ){  return  (JSX) }
let vchild = <BuyCount   c={5}/>

②类式组件 —— 面向对象的编程思想(Java)

class  BuyCount  extends  React.Component{
	render(){ log(this.props) return (JSX) }
}
let vchild = <BuyCount   c={5}/>

6.React中事件处理函数中this指向丢失问题

//解决方案1:使用箭头函数
class  BuyCount  extends  React.Component{
     f1 = ( )=>{ log(this) }
	render(){ return <button onClick={this.f1}></button>》 }
}
//解决方案2:使用箭头函数(可以传参)
class  BuyCount  extends  React.Component{
     f1( 形参 ){ log(this) }
	render(){ return <button onClick={ ()=>this.f1(实参) }></button>》 }
}
//解决方案3:使用bind固定this的指向
class  BuyCount  extends  React.Component{
     f1 = (){ log(this) } 
	render(){ return <button onClick={ this.f1.bind( this ) }></button>》 }
}
//解决方案4:使用bind固定this的指向
class  BuyCount  extends  React.Component{
     constructor(){
        super()
        this.f1 = this.f1.bind( this )
     }
     f1(){ log(this) } 
	render(){ return <button onClick={ this.f1 }></button> }
}

一、React概述

英文官网:https://reactjs.org/
中文网站:https://zh-hans.reactjs.org/
用于构建用户界面的 JavaScript 库 —— 其核心功能中不涉及HTML和CSS
其特点有三个:
①声明式 / 数据响应式
②组件化编程
③一次学习,到处编写 —— React可以创建网站、H5、WebApp、原生App

项目中使用React的两种方式:
方式1:脚本引入式

<script  src="react.js"></script>
<script  src="react-dom.js"></script>
<script  src="babel.js"></script>

方式2:脚手架方式 在服务器端编译/渲染
使用方法:
①确保Node.js版本号达标

  node  -v       必须确保版本号>=14.0.0

②下载全局脚手架工具 —— create-react-app

  npm   i   -g    create-react-app

③运行脚手架工具,创建空白项目

  create-react-app   项目名       //注意:React项目名不能包含大写字母
  提示:上述②③两步可以使用一行命令代替: npx  create-react-app  项目名

④进入空白项目

  cd  项目名

⑤启动其中的开发服务器,浏览器会自动打开,显示默认首页

  npm  start

二、JSX

JSX:JavaScript XML,使用XML语法创建JS对象的技术。这种语法本身是TS的一部分,与React没有必然的联系(不过JSX确实是因为React而流行)。
使用JSX需要注意:
1.语法类似于XML(严格来说不是HTML)
2.有且只能有一个根元素,根元素下面可以有多个子/孙元素;如果根元素有多个,那就在外面再套一个父元素:<></>、<React.Fragment></React.Fragment>
3.标签/属性名严格区分大小写
4.标签必须闭合
5.因为浏览器不支持TS语法,也就不支持JSX语法;——必须使用一款TS编译器,把JSX语法转换为标准JS语句
6.注意:JSX的本质是运行于严格模式下的React.createElement( ),是JS不是HTML!!!React项目可以不用JSX,但是使用了JSX,创建虚拟DOM元素语法会变得简单
7.JSX语法中可以任意添加换行
8.JSX中的注释: {/* 注释内容 */}
9.JSX中元素可以使用的属性与HTML标签的属性大体类似,但是有些是不同的,例如:

HTML: class				JSX:className
HTML: onclick / onkeyup	JSX:onClick / onKeyUp

10.JSX中可以执行数据绑定,不论是哪种绑定(内容绑定/属性绑定/样式绑定/事件绑定…)语法都是一样的:{ 表达式 }

<div  title={表达式}  style={表达式}  onClick={表达式}>{表达式}</div>
注意:React中“内容绑定”禁止绑定Object!!!“样式绑定”必须绑定一个样式Object!!!

三、React中自定义组件

React中提供了两种创建自定义组件的语法:
语法1: 函数式组件(Function Component)

function ZhRating( props ){
    return <div>⭐⭐⭐⭐⭐</div>
}
let vchild = <ZhRating color="#f00" count={5}/>

注意:React要求,HTML元素对应的JSX标签必须用纯小写;自定义组件名必须采用大驼峰命名法(每个单词首字母必须大写)

语法2: 类式组件(Class Component)

class ZhRating  extends  React.Component {
    render( ){
       //使用this.props读取组件属性
       return <div>⭐⭐⭐⭐⭐</div>
    }
}
let vchild = <ZhRating color="#f00" count={5}/>

四、重点&难点&面试题:React中有时this指向会丢失/this会指向undefined,为什么?如何解决?

一般情况下,class中的方法访问当前类中的属性或其它方法,都要使用this——它指向当前类的当前实例;
有一种特例:JSX事件处理函数中的this,却指向undefined!!!
可能性1:this指向事件源对象? 否——虚拟DOM元素不能做事件源
可能性2:this指向class或实例? 否——类的实例方法赋值给另一个对象了
可能性3:this指向window? 否——Babel编译后的结果运行在严格模式
可能性4:this指向undefined? 是
解决方案:
方案1:使用箭头函数(不能传参)

f1 = ()=>{  log(this)  }
<button onClick={ this.f1 }>

方案2:使用箭头函数(可以传参)

f1 = function( ){  log(this)  }
<button onClick={ ( )=>this.f1( ) }>

方案3:使用bind固定this指向(多次bind会生成多个副本)

f1 = function( ){  log(this)  }
<button onClick={ this.f1.bind( this ) }>

方案4:使用bind固定this指向(生成且仅生成一次副本)

constructor(){
   super()
   this.f1 = this.f1.bind( this )
}
f1 = function( ){  log(this)  }
<button onClick={ this.f1 }>

五、组件的状态数据(State)

面试题:Vue.js和React的区别?尤雨溪答:
Vue.js中的数据响应式采用“Push-Based”机制——数据的改变会自动推送出去,告诉渲染系统重新渲染;

data: { return {  count: 1 } }
	this.count = 2		//此处的修改会执行两项任务:①修改模型变量  ②通知渲染系统重新渲染整个视图

React中的数据响应式采用“Pull-Based”机制,即组件的模型数据改变必须手工通知渲染系统。

state = {  count:  1 }
this.state.count = 2		//此处的修改仅仅修改了变量的值,不会通知渲染系统
this.setState({ count: 2 })   //setState()会修改状态变量,并通知渲染系统

面试题:关于setState()方法
① setState()方法只会覆盖state中的同名属性,而不丢弃其它属性
② setState()方法是异步执行的,启动渲染系统很耗时,不会立即进行
③ setState()因为是异步的,所以它后面的语句会先执行,然后才去修改状态变量;如果想查看修改后的状态数据,必须放在第二个参数(状态修改并重新渲染后的回调) setState( state, callback )

六、JSX中的数据绑定 —— React中没有指令的概念

注意:JS中变量、常量、运算式、调用方法都是“表达式”;但是if、for、function不是“表达式”!!!{ }中只能放置表达式!!!
内容绑定:<div>{表达式}</div>
属性绑定:<img src={表达式}/>
样式绑定:<div className={表达式} style={表达式}>
事件绑定:<button onClick={函数} onmouseenter={函数}>
双向数据绑定:
条件渲染:
仿v-show:<any style={{display: this.state.show ? "block" : "none"}}/>
仿v-if:{ 判定表达式 && (JSX) } { 判定表达式 ? (JSX1) : (JSX2) }
列表渲染:

七、class组件的生命周期方法

第一阶段:挂载阶段

constructor():创建组件对象
render():渲染组件的内容
componentDidMount():组件完成挂载

第二阶段:更新阶段(state/props发生改变)

shouldComponentUpdate():此次数据改变应该重新渲染组件吗?
render():重新渲染组件内容
componentDidUpdate():组件完成更新

第三阶段:卸载阶段

componentWillUnmount():组件即将卸载

function Child( props ){

}

八、重点/难点/面试题:Hook(钩子)

自从React诞生,“函数式组件”功能一直有缺失:没有状态、没有生命周期方法 —— 没有父类,导致函数式组件只能编写一些简单的固定内容的组件。
V16.8开始,官方为“函数式组件”弥补了不足——增加了“Hook”的概念,同时由于自身的优势(天然没有this),导致越来越多的程序员开始偏向使用“函数式组件”。
当前的项目中,可以同时使用“类式组件”和“函数式组件”。

Hook的定义:
①钩子,用于勾住/增加一些扩展的功能
②每个Hook都是一个函数,都必须以 use 开头,例如:useState()、useRef()
③Hook函数只能在“函数式组件”中使用,不能用于“类式组件”
④Hook函数只能在“函数式组件”的最顶层调用,不能在内层调用

function Child(){
	useState()  				   //合法!最顶层
	f1=function(){  useState() } 	//错误!
	if(){ useState() }  			//错误!
	for(){ useState() }  			//错误!
	useState()  				   //合法!最顶层
}

React官方提供的常用钩子之一 —— useState( ):为组件添加状态变量

import  { useState }  from  'react'
let  [ 状态变量名,  修改状态变量的方法名 ] = useState( 状态变量初始值 )

React官方提供的常用钩子之二 —— useEffect( ):为组件添加生命周期方法

//生命周期方法1
useEffect( ()=>{
    //生命周期方法1 = 组件挂载 + 任意数据更新
} )
//生命周期方法2
useEffect( ()=>{
    //生命周期方法2 = 组件挂载 + 指定数据更新
} , [count, age, ...] )     //依赖列表有内容
//生命周期方法3
useEffect( ()=>{
    //生命周期方法3 = 组件挂载 
} , [ ] )     //依赖列表为空
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值