React面试总结

1.jsx基本使用

  • 变量,表达式
    在render函数里使用 {this.state.xxx}表达式获取变量
  • class style写法是
//如果要插入一段原生html,可以使用
</p>
  const ralHtml = `<span>asdasdasd</span><pdangerslySetInnerHTML={ralHtml}>
</p>`
  • 子元素和组件
    条件判断
    1.if else
    2.三元表达式
    3.逻辑运算符&& ||

  • 渲染列表
    1.map
    2.key

2.事件

1.bind this 性能优化小知识点,可以在constructor里面修改函数this的指向

constructor(props) {
  super(props)
  this.getFirstRequest = this.getFirstRequest.bind(this)
}

或者使用静态方法(箭头函数,this指向当前实例)

//改变状态前后都想做一些事情:
this.setState((prevState)=>{
    // prevState:是旧值
    console.log("prevState",prevState)
    return {
        age:15
    }
},()=>{
    // this.state:就是新值。
    console.log(this.state.age);
}); 

2.关于event参数
3.传递自定义参数

3.react事件和dom事件

react中的event是syntheticEvent(合成事件),模拟出来DOM事件所有能力
event.nativeEvent是原生事件对象
所有的事件,都被挂载到doucument上(react16),
react17开始事件绑定到root上
和dom事件不一样和vue事件也不一样

//传递参数
clickHandle(id,title,event){
  //最后追加一个参数,即可接收event
}

4.react表单知识点串讲

1.受控组件

render(){
  return (<div>
          <p>{this.state.name}</p>
          <input value={this.state.name} onchange=(this.changeValue)/>
    </div>
  )
}
//textArea 这些的值,要用vue,而不是
<textArea>{this.state.value}</textArea>

5.react父子组件通讯

1.props传递数据
2.props传递函数
3.props类型检查
状态提升,意思是把数据放在在高一层的组件,高层组件来做数据跟改和数据分发,子组件只用来渲染

6.setState为何使用不可变值

setState
1.不可变值
不要直接操作不可变值,要用this.setState()
不能对this.state.arr直接使用push pop splice等,这样违反不可变值
不仅数组,object也是一样,最好的做法就是生成一份副本,再对副本做修改,然后使用this.setState()进行设置
在生命周期shouldComponentUpdate会有影响

//不要这样使用
this.setState({list:this.state.list.splice(0,3)})

2.什么建议传递给setState函数的参数是回调函数而不是对象?
因为,this.setState()函数内部是异步执行的。

this.setState({
     msg:"hello"
});
console.log(this.state.msg);// 这个值不是hello

换一种写法

this.setState({
count:this.state.count+1
},()=>{
//这里获取的是改变的最新的值
console.log(this.state.count)
})
//这里是之前未改变的值
console.log(this.state.count)

setState直接使用是异步的,在setTimeout和自定义dom事件中使用是同步的
3.可能会被合并
传入对象,会被合并,执行结果只一次 +1,类似于(Object.assgin)

this.setState({
count:this.state.count+1
})
this.setState({
count:this.state.count+1
})
this.setState({
count:this.state.count+1
})
//相当于只执行了一次
this.setState({
count:0+1
})

传入函数,不会被合并,执行结果+3

this,.setState((prevState,props)=>{
  return{
  count:prevState.count+1
  }
})
this,.setState((prevState,props)=>{
  return{
  count:prevState.count+1
  }
})
this,.setState((prevState,props)=>{
  return{
  count:prevState.count+1
  }
})
//结果会是3,6,9依次往上叠加,

7.组件生命周期

  • 1 React16
// 组件将要挂载
constructor(props){
  super(props)
}
componentWillMount(){
  console.log("Count---componentWillMount")
} 
// 渲染组件  常用
render(){
  return(
    <div></div>
  )
}
//  组件挂在完毕的钩子  常用
componentDidMount(){
  console.log("Count---componentDidMount")
}
// 组件将要卸载  常用
componentWillUnmount(){
  console.log("Count---componentWillUnmount")
}
// 控制组件更新的阀门 返回true继续  false 结束
shouldComponentUpdate (){
  console.log("Count---shouldComponentUpdate")
  return true
}
// 组件将要更新
componentWillUpdate(){
  console.log("Count---componentWillUpdate")
}
// 组件更新完成
componentDidUpdate(){
  console.log("Count---componentDidUpdate")
}
react生命周期(16).png
  • React17
// 构造器
constructor(props){
  super(props)
}
//  若 state 的值在任何时候都取决于 props
static getDerivedStateFromProps(props,state){
  console.log("Count---getDerivedStateFromProps",props,state)
  return null
}
// 在更新之前获取快照
getSnapshotBeforeUpdate(snapshot){
  console.log("Count---getSnapshotBeforeUpdate",snapshot)
  return "test"
}
// 渲染组件  常用
render(){
  return(
     <div></div>
  )
}
//  组件挂在完毕的钩子  常用
componentDidMount(){
  console.log("Count---componentDidMount")
}   
// 组件将要卸载 常用
componentWillUnmount(){
  console.log("Count---componentWillUnmount")
}
// 控制组件更新的阀门 返回true继续  false 结束
shouldComponentUpdate (){
  console.log("Count---shouldComponentUpdate")
  return true
}
// 组件更新完成
componentDidUpdate(preProps,preState,snapshotVlaue){
  console.log("Count---componentDidUpdate",preProps,preState,snapshotVlaue)
}

react生命周期(17).png

8.react函数组件和class组件的区别

1.纯函数,输入props,输入jsx
2.没有实例,没有生命周期,没有state
3.不能扩展其他方法

9.非受控组件

1.ref(三种方式 字符串 函数回调 create_ref)
2.defaultValue defaultChecked
3手动操作DOM元素
非受控组件
必须手动操作DOM元素,setState实现不了
文件上传
某些富文本编辑器,需要传入DOM元素

10.portals 传送门

组件默认会按照既定层次嵌套渲染
如何让组件渲染到父组件以外
应用场景: 对话框、悬浮卡以及提示框:
overflow:hidden(父级设置了BFC)
父组件z-index值太小
fixed需要放在body第一层级

render(){
  //正常使用
return <div class="modal">
    {this.props.children}
</div>
}
//使用Portals渲染到body上
return ReactDom.createPortal(
<div class="modal">
    {this.props.children}
</div>,document.body //后面这个document.body值的意思是渲染到body里面
)

11.react Context

主要用于设置公共信息(语言,主题)

//创建Context默认值
  const ThemeContext = React.createContext('light')
  //在最外层的父组件 渲染时用<ThemeContext.Provider value={this.state.theme}>包裹
render(){
return 
<ThemeContext.Provider value={this.state.theme}>
//里面是一些子组件
<ThemedBUtton />
<ThemeContext.Provider>
}
//子组件获取context值(class组件)
class ThemedBUtton extends React.Component{
render(){
const theme = this.context//react会往上找最近的provider
return <div>
    <p>{theme} </p>
</div>
  }
}
themedButton.contextType = ThemeContext //指定conterxtType

//也可以写成
static contextType = themeContext
//函数组件获取
function theLinkl(props){
return <ThemeContext.Consumer>
{value => <p>link's theme is {value}</p>}
</ThemeContext.Consumer>
}

12.异步组件
import()
react.lazy
react.suspense

//异步加载当前组件
const ContextDemo= React.lazy(()=>import('./ContextDemo'))
class App extends React.Component{
constructor(props){
  super(props)
  }
render(){
  return <div>  
  <React.Suspense fallBack={<div>Loading...</div}
      <ContextDemo/>
</React.Suspense>
</div>
}
}

13.性能优化

  • shouldComponentUpdate(简称SCU),必须配合不可变值使用
    scu基本用法
shouldComponentUpdate(nextProps,nextState){
  if(nextState.count !== this.state.count){
    return true //刻意渲染
  }
  return false
}
  • PureComponent(纯组件)和React.memo
    纯组件其实也是scu中进行了浅比较,只比对了第一层是否一样
    函数组件中的pureComponent memo
    -不可变值immutable.js
    1.彻底拥抱不可变值
    2.基于共享数据(不是深拷贝),速度好
    3.有一定的学习成本和迁移成本,按需使用

14.react高阶组件

HOC

//高阶组件不是一种功能,而是一种模式
const HOCFactory = (COmponent)=>{
  class HOC extends React.Component{
    //在此定义多个组件的公共逻辑
  render(){
    return <Component {...this.props} />//返回拼装结果
   }
  }
  return HOC
}
const EnhancedComponent1 = HOCFactory(WrappedComponent1)
const EnhancedComponent2 = HOCFactory(WrappedComponent2)
  • HOC vs Render Props
    1.HOC:模式简单,但会增加组件层级
    2.render props:代码简洁,学习成本较高
    3.按需使用
    在react中实现公共逻辑的抽离,使用HOC或者render props

15.Redux使用

1.和vuex作用相同,但比Vuex学习成本高
2.不可变值,纯函数
3.面试常考

基本概念

  • 1.store state
  1. 将state、action、reducer联系在一起的对象
  2. 如何得到此对象?
  1. import {createStore} from 'redux'
  2. import reducer from './reducers'
  3. const store = createStore(reducer)
  1. 此对象的功能?
  1. getState(): 得到state
  2. dispatch(action): 分发action, 触发reducer调用, 产生新的state
  3. subscribe(listener): 注册监听, 当产生了新的state时, 自动调用
  • 2.action
  1. 动作的对象
  2. 包含2个属性

type:标识属性, 值为字符串, 唯一, 必要属性
data:数据属性, 值类型任意, 可选属性

  1. 例子:
{ type: 'ADD_STUDENT',data:{name:  'tom',age:18} }

3.reducer

  1. 用于初始化状态、加工状态。
  2. 加工时,根据旧的state和action, 产生新的state的纯函数。
  • 单向数据流
    dispatch(action)
    reducer -> newState(不可变值)
    subscribe 触发通知
  • react-redux
    Provider
    connect
    mapStateToProps mapDispatchToProps
    在需要使用的index.js文件里面引入Provider
//使用Provider整体传入store对象
import {Privder} from 'react-redux'
import todoApp from './reducers'
import App from './component/App'
let store = createStore(todoApp)
export store = function(){
  return <Provider store={store}> 
  <App />
</Provider>
}
//需要消费store的子组件里面需要调用一下connect方法
AddTodo = connect()(AddTodo)
export default AddTodo
//调用connect()后dispatch已经被注入到该组件中
//dispatch一个action到 effects =>reducer(不可变值)=>返回新的值=>store修改=>触发订阅跟新数据=>页面刷新

  • 异步action
    首先在创建store的时候要引入
import {createStore,applyMiddleWare} from 'redux'
import thunk from 'redux-thunk'
import rootReducer from './reducers/index'
const store = createStrore(rootReducer,applyMiddleWare(thunk ))
//在使用action 的地方 以前是返回一个对象,现在返回一个函数
  • 中间件
    中间件原理,大致就是把当前的dispatch做了下改造,先把当前的disptch用一个
let next = dispatch
console.log(1)
next()
console.log(2)

16.react-router路由模式

1.hash模式(默认 兼容性更强)
2.h5history模式(更美观)
3.后者需要后端支持,因此无特殊需求选择前者

import{hashRouter as Router,Switch,Route} from 'react-router-dom'
//BromserRouter as Router
function RouterComponent(){
  return(
    <router>
      <Switch>
          <route path="*">
          //这里面包裹组件
          </route>
      </Switch>
    </router>
  )
}

17jsx本质

通过createelement函数 第一个参数是tag,第二个参数是属性也就是一个对象,没有的话传入null,第三个参数可以是数组,数组里面继续是createelement函数对应的子元素,依次。也可以打散挨个传入。最终返回一个vnode 在通过patch渲染

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 219,490评论 6 508
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,581评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 165,830评论 0 356
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,957评论 1 295
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,974评论 6 393
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,754评论 1 307
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,464评论 3 420
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,357评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,847评论 1 317
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,995评论 3 338
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,137评论 1 351
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,819评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,482评论 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 32,023评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,149评论 1 272
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,409评论 3 373
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 45,086评论 2 355

推荐阅读更多精彩内容

  • 目标 掌握类组件的定义和使用; 掌握 React 组件间通信的方式; 掌握类组件的生命周期。 内容 在 React...
    magic_pill阅读 296评论 0 0
  • 性能优化 性能优化,永远是面试的重点,性能优化对于 React 更加重要 在页面中使用了setTimout()、a...
    Actoress阅读 1,637评论 0 5
  • jsx基本使用 变量,表达式在render函数里使用 {this.state.xxx}表达式获取变量 class ...
    懵逼猫9527阅读 284评论 0 2
  • 作为一个合格的开发者,不要只满足于编写了可以运行的代码。而要了解代码背后的工作原理;不要只满足于自己的程序...
    六个周阅读 8,449评论 1 33
  • 常见面试题:1.React组件如何通讯?2.JSX本质是什么?3.context是什么?有何用途?4.should...
    洛珎阅读 723评论 0 2