react-入门

基础认识

  • 官网
  • 特点
  • 声明式编程
  • 组件化
  • 支持客户端和服务端渲染
  • 高效
    • 虚拟DOM,不总是直接操作DOM,只是减少DOM的操作,操作虚拟DOM不会对页面进行重绘,当渲染的时候,才会进行渲染
    • DOM Diff 算法,最小化页面重绘,就是当页面变化时,通过计算那部分需要重绘,只重绘当前部分,减少页面的重绘区域
  • 单向数据流
  • js文件
  • react.js:react的核心库
  • react-dom.js:提供操作DOM的react扩展
  • babel.js:解析jsx语法
<div id="app"></div>
 <script src="js/react.development.js"></script>
    <script src="js/react-dom.development.js"></script>
 <script src="js/babel.min.js"></script>
    <script type="text/babel">
        // 创建虚拟DOM元素对象
        let vDom = <h1>react hello</h1>
 // 将虚拟DOM渲染到页面真实DOM容器中
 ReactDOM.render(vDom,document.getElementById(‘app‘))
 
 </script>

JSX

  • react提供了创建虚拟DOM的方法
  • 虚拟DOM对象最终都会被react转换为真实的DOM
  • 编码时,只需要操作react的虚拟DOM相关数据,react会转换为真实DOM变化而更新界面
// react直接操作和JSX操作对比
<script type="text/javascript">
    const msg = ‘MSG content‘
const msgId = ‘App‘

// 创建虚拟DOM
// const VDom1 = React.createElement(‘标签名‘,{id:‘xxx‘},‘内容‘)
const vDom1 = React.createElement(‘h1‘, {
    id: msgId.toLowerCase()
}, msg.toLowerCase())

// 渲染虚拟DOM
ReactDOM.render(vDom1, document.getElementById(‘app1‘))
</script>

<script type="text/babel">
    // 创建虚拟DOM 
    const vDom2 = <h2 id={msgId.toUpperCase()}>{msg.toLowerCase()}</h2>;

// 渲染虚拟DOM 
ReactDOM.render(vDom2,document.getElementById(‘app2‘))
</script>
  • 动态渲染一个列表
  • 使用数组的Map函数返回所需要的列表内容
let arrs = [111,222,333,444]
// 创建虚拟DOM 
const ul = (
    <ul>
    {
        arrs.map((name,index) => <li key={index}>{name}</li>)
 }
 </ul>
)

// 渲染虚拟DOM 
ReactDOM.render(ul, document.getElementById(‘app1‘))

组件

  • 工厂函数创建组件
  • 使用工厂函数的效率比使用class高,因为工厂函数中不需要创建一系列的对象之类的
  • 当组件有状态(state)的时候就不适合使用了
// 工厂函数创建组件
function MyCom(){
    return <h2>工厂函数创建组件</h2> 
}
 
// 渲染组件标签
// <MyCom />必须这么写
// <MyCom>这么写是错误的
ReactDOM.render(<MyCom />,document.getElementById(‘app‘))
  • class创建组件
// class定义组件
class MyCom2 extends React.Component{
    render(){
        return <h3>class定义组件</h3>
 }
}

// 渲染组件标签
// <MyCom2 />必须这么写
// <MyCom2>这么写是错误的
ReactDOM.render(<MyCom2 />,document.getElementById(‘app‘))

组件三大属性

state

  • state是组件对象的最重要的属性之一,值是一个对象,这个对象可以包含多个数据
  • 组件被称为状态机,通过更新组件的state来更新对应的页面显示,就是通过state来控制组件的重新渲染(重绘)

  • 初始化状态

constructor(props){
    super(props)
    this.state = {
        stateProp1:value1,
        stateProp2:value2
    }
}
  • 读取某个状态值
this.state.statePropertyName
  • 更新状态:组件重新渲染
this.setState({
    stateProp1:newValue1,
    stateProp2:newValue2
})
  • 案例:点击切换内容
//定义组件
class Like extends React.Component{
    constructor(props){
        super(props)
        //初始化状态state
        this.state = {
            isShow:false
        }
        
        //将新增方法中的this强制绑定为组件对象
        this.handleClick = this.handleClick.bind(this)
    }
    
    // 新添加的方法:内置的this默认不是组件对象,是一个undefined
    handleClick(){
        //获取原始状态并取反
        let isShow = !this.state.isShow
        // 设置状态
        this.setState({isShow})
    }
    
    // React.Component中本身就具有render函数,在class中只是重写组件类的方法render,所以这里的this指向没有问题
    render(){
        //获取状态
        // const isShow = this.state.isShow
        const {isShow} = this.state
        //onClick是react的,区分原生的onclick
        // this.handleClick.bind(this)也可以,但是这种效率比较低,因为每次render都会执行一次bind进行绑定,而在constructor中只会在初始化的时候绑定一次
        return <h1 onClick={this.handleClick}>{isShow ? ‘我是帅哥‘ : ‘帅哥是我‘}</h1>
 }
 
}

//渲染组件
ReactDOM.render(<Like/>,document.getElementById(‘app‘))

props

  • 案例:定义一个显示个人信息的组件
  • 姓名必须指定
  • 性别默认为男
  • 年龄默认为18
//创建组件
/* function Person(props) {
 return (
 <ul>
 <li>姓名:{props.name}</li>
 <li>性别:{props.sex}</li>
 <li>年龄:{props.age}</li>
 </ul>
 )
} */

// class创建
class Person extends React.Component{
    render(){
        return (
            <ul>
            <li>姓名:{this.props.name}</li>
 <li>性别:{this.props.sex}</li>
            <li>年龄:{this.props.age}</li>
 </ul>
        )
    }
}
        
//属性默认值
Person.defaultProps = {
    sex:‘man‘,
    age:18
}

//属性的类型和必填
Person.propTypes = {
    name:PropTypes.string.isRequired,
    age:PropTypes.number
}

const p1 = {
    name:‘nordon‘,
    sex:‘man‘,
    age:22
}
// 渲染组件
// ReactDOM.render(<Person name={p1.name} sex={p1.sex} age={p1.age} />,document.getElementById(‘app‘))
ReactDOM.render(<Person {...p1} />,document.getElementById(‘app‘))

const p2 = {
 name:‘lisan‘
} 
ReactDOM.render(<Person name={p2.name} age={19}/>,document.getElementById(‘app2‘))

refs与事件处理

  • 案例:获取input中的值
//定义组件
class MyInput extends React.Component {
            
    constructor(props){
        super(props)
        this.handleClick = this.handleClick.bind(this)
        this.handleBlur = this.handleBlur.bind(this)
    }

    handleClick(){
        let input1 = this.refs.inputValue
        console.log(input1.value)
        console.log(this.newInput.value)
    }

    handleBlur(event){
        console.log(event.target.value)
    }

    render (){
        return (
            <div>
                <input type="text" ref="inputValue" />&nbsp;&nbsp;
 <input type="text" ref={inputValue => this.newInput = inputValue } />&nbsp;&nbsp;
                <button onClick={this.handleClick}>获取值</button>&nbsp;&nbsp;
 <input type="text" placeholder="失去焦点获取值" onBlur={this.handleBlur} />
            </div>
 )
 }
}
 
//渲染组件
ReactDOM.render(<MyInput/>,document.getElementById(‘app‘))

ToDolist

  • 简单的tdolist案例
// 定义组件
// 组件状态的更改必须在当前组件中进行
class App extends React.Component{ 

    constructor(props){
        super(props)

        this.state = {
            todos:[‘111‘,‘222‘,‘333‘]
        }

        this.addTodo = this.addTodo.bind(this)
    }

    addTodo(todo){
        let {todos} = this.state
        todos.unshift(todo)
        this.setState({
            todos
        })
    }

    render(){ 
        const {todos} = this.state
        return (
            <div>
            <h1>this is todolist demo</h1>
 <Add count={todos.length} addTodo={this.addTodo} />
            <List todos={todos} />
 </div>
        ) 
    }
}

class Add extends React.Component{ 
    constructor(props){
        super(props)

        this.handleAdd = this.handleAdd.bind(this)
    }
    handleAdd(){
        // console.log(this.refs.content.value);
        // <input type="text" ref="content" /> &nbsp;&nbsp;
        // console.log(this.newTodos.value);
        const data = this.newTodos.value
        if(!data){
            return false;
        }
        this.newTodos.value = ‘‘
        this.props.addTodo(data)
    }
    render(){
        return (
            <div>
            <input  type="text" ref={inputValue => this.newTodos = inputValue} /> &nbsp;&nbsp;
 <button onClick={this.handleAdd}>按钮#{this.props.count + 1}</button>
            </div>
 )
 }
}
Add.propTypes = {
 count:PropTypes.number.isRequired,
 addTodo:PropTypes.func.isRequired
}

class List extends React.Component{

 render(){
 let {todos} = this.props
 return (
 <div>
 <ul>
 {todos.map( (item,index) => <li key={index}>{item}</li> )}
            </ul>
 </div>
        )
    }
}
// name:PropTypes.string.isRequired,
List.propTypes = {
    todos:PropTypes.array.isRequired
}

// 渲染组件
ReactDOM.render(<App/>,document.getElementById(‘app‘))

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


react 中的高阶组件主要是对于 hooks 之前的类组件来说的,如果组件之中有复用的代码,需要重新创建一个父类,父类中存储公共代码,返回子类,同时把公用属性...
我们上一节了解了组件的更新机制,但是只是停留在表层上,例如我们的 setState 函数式同步执行的,我们的事件处理直接绑定在了 dom 元素上,这些都跟 re...
我们上一节了解了 react 的虚拟 dom 的格式,如何把虚拟 dom 转为真实 dom 进行挂载。其实函数是组件和类组件也是在这个基础上包裹了一层,一个是调...
react 本身提供了克隆组件的方法,但是平时开发中可能很少使用,可能是不了解。我公司的项目就没有使用,但是在很多三方库中都有使用。本小节我们来学习下如果使用该...
mobx 是一个简单可扩展的状态管理库,中文官网链接。小编在接触 react 就一直使用 mobx 库,上手简单不复杂。
我们在平常的开发中不可避免的会有很多列表渲染逻辑,在 pc 端可以使用分页进行渲染数限制,在移动端可以使用下拉加载更多。但是对于大量的列表渲染,特别像有实时数据...
本小节开始前,我们先答复下一个同学的问题。上一小节发布后,有小伙伴后台来信问到:‘小编你只讲了类组件中怎么使用 ref,那在函数式组件中怎么使用呢?’。确实我们...
上一小节我们了解了固定高度的滚动列表实现,因为是固定高度所以容器总高度和每个元素的 size、offset 很容易得到,这种场景也适合我们常见的大部分场景,例如...
上一小节我们处理了 setState 的批量更新机制,但是我们有两个遗漏点,一个是源码中的 setState 可以传入函数,同时 setState 可以传入第二...
我们知道 react 进行页面渲染或者刷新的时候,会从根节点到子节点全部执行一遍,即使子组件中没有状态的改变,也会执行。这就造成了性能不必要的浪费。之前我们了解...
在平时工作中的某些场景下,你可能想在整个组件树中传递数据,但却不想手动地通过 props 属性在每一层传递属性,contextAPI 应用而生。
楼主最近入职新单位了,恰好新单位使用的技术栈是 react,因为之前一直进行的是 vue2/vue3 和小程序开发,对于这些技术栈实现机制也有一些了解,最少面试...
我们上一节了了解了函数式组件和类组件的处理方式,本质就是处理基于 babel 处理后的 type 类型,最后还是要处理虚拟 dom。本小节我们学习下组件的更新机...
前面几节我们学习了解了 react 的渲染机制和生命周期,本节我们正式进入基本面试必考的核心地带 -- diff 算法,了解如何优化和复用 dom 操作的,还有...
我们在之前已经学习过 react 生命周期,但是在 16 版本中 will 类的生命周期进行了废除,虽然依然可以用,但是需要加上 UNSAFE 开头,表示是不安...
上一小节我们学习了 react 中类组件的优化方式,对于 hooks 为主流的函数式编程,react 也提供了优化方式 memo 方法,本小节我们来了解下它的用...
开源不易,感谢你的支持,❤ star me if you like concent ^_^
hel-micro,模块联邦sdk化,免构建、热更新、工具链无关的微模块方案 ,欢迎关注与了解
本文主题围绕concent的setup和react的五把钩子来展开,既然提到了setup就离不开composition api这个关键词,准确的说setup是由...
ReactsetState的执行是异步还是同步官方文档是这么说的setState()doesnotalwaysimmediatelyupdatethecomponent.Itmaybatchordefertheupdateuntillater.Thismakesreadingthis.staterightaftercallingsetState()apotentialpitfall.Instead,usecom