rem和em的区别
1. em
是一个相对单位。相对于当前对象内文本的font-size,
- em的值并不是固定的
- em会继承父元素的字体大小
- 如果当前文本的字体尺寸没有设置,则相对于浏览器的默认字体尺寸
2. rem
是一个相对单位。是相对HTML根元素。
- 特点:
- rem为元素设定字体大小的时候,是相对于根元素进行计算的。
- 当我们改变根元素下的字体大小时,下面的大小都会改变。
- 通过rem既可以做到只修改根元素就可以成比例的调整所有字体,又可以避免字体大小逐层复合的连锁反应。
引用类型和基本类型的区别
1.基本类型包括:
string,number,boolean,null,undefined,symbol
2. 引用类型包括:
Function,Array,Object
基本类型和引用类型也有人叫原始类型和对象类型,拥有方法的类型和不能拥有方法的类型,可变类型和不可变类型
3.基本类型
基本类型是按值访问的,引用类型是按引用访问
由于基本类型本身是没有方法和属性的,所以他的值是不可变的
引用类型也可以说是对象了,对象是属性和方法的集合。
也就是说引用类型可以拥有属性和方法,属性又可以包含基本类型和引用类型。
说说你了解的ES6新增特性
1.let声明变量和const声明常量
let和const两个都有块级作用域但不同的是
const 声明的是常量值不可以被修改
let 声明的是变量值可以被修改
2.箭头函数
Es6中定义函数不再使用Function而是替换成了()=>来定义
箭头函数本身是没有this的
谁定义它this就指向谁,如果没有this就指向window
3.import和export 导入导出
ES6标准中,Js原生支持模块(module)。将JS代码分割成不同功能的小块进行模块化,将不同功能的代码分别写在不同文件中,各模块只需导出公共接口部分,然后通过模块的导入的方式可以在其他地方使用
promise
首先primise是什么?
1、主要用于异步计算
2、可以将异步操作队列化,按照期望的顺序执行,返回符合预期的结果
3、可以在对象之间传递和操作promise,帮助我们处理队列
为什么虚拟dom会提高性能?
虚拟dom相当于js和真实dom中间加了一个缓存,利用dom diff 算法,避免了没有必要的dom操作,从而提高性能
虚拟DOM中Key的作用
key是虚拟DOM对象的标识,在更新显示时key起着极其重要的作用,当状态的数据发生变化时,react会根据新数据生产新的虚拟dom,随后react进行新虚拟dom与旧虚拟dom的diff比较,比较规则如下:
1.旧虚拟dom中找到了新虚拟dom相同的key
(1)若虚拟dom中内容没变,直接使用之前的真实dom
(2)若虚拟dom中内容变了,则生成新的真实dom,随后替换掉页面中之前的真实dom
2.旧虚拟dom中未找到与新虚拟dom相同的key
根据数据创建新的真实dom,随后渲染到页面
什么是eventLoop?
Event Loop即事件循环,是指浏览器或Node的一种解决javaScript单线程运行时,不会阻塞的一种机制,也就是我们经常使用异步的原理
事件循环的进程模型
选择当前要执行的任务队列,选择任务队列最先进入的任务,如果任务队列为空即null,则跳转到微任务
将事件循环中的任务设置为已选择任务
执行任务
将事件循环中当前运行任务设置为null
将已经运行完成的任务从任务队列中删除
更新页面渲染
返回第一步
React函数组件和类组件的区别
- 语法上的区别:
函数是组件是一个纯函数,它需要接受props参数并且返回一个React元素就可以。类组件是需要继承React.Component的,而且class组件需要创建render并且返回React元素,语法上来讲更复杂
- 调用方式:
函数式组件可以直接调用。返回一个新的React元素;类组件再调用时是需要创建一个实例的,然后通过调用实例里的render方法来返回一个React元素
- 状态管理
函数式组件没有状态管理,类组件有状态管理。
- 使用场景
类组件没有具体的要求。函数式组件一般是在大型项目中来分割大组件(函数式组件不用创建实例,所以更高效),一般情况下能用函数式组件就不用类组件,提升效率。
React 组件之间传递值和事件的几种方式
- 使用 props
在函数组件中使用 props
父组件
<Welcome fname="gxh" func={ func}/>;
子组件
function Welcome(props) {
this.props.func() // 触发父组件事件
return <h1>Hello, {props.fname}</h1>; // 获取值
}在class 组件中使用 props
在class 组件中使用 props
父组件
<Welcome cname="gxh" cfunc={this.func}/>;
子组件
class Welcome extends React.Component {
this.props.cfunc() // 触发父组件事件
render() {
return <h1>Hello, {this.props.cname}</h1>; // 获取值
}
}
Props的只读性:组件无论是使用函数声明还是通过 class 声明,都决不能修改自身的 props
2、使用 Context
Context提供了一个无需为每层组件手动添加 props,就能在组件树间进行数据传递的方法。
在一个典型的 React 应用中,数据是通过 props属性自上而下(由父及子)进行传递的,但此种用法对于某些类型的属性而言是极其繁琐的,这些属性是应用程序中许多组件都需要的。Context提供了一种在组件之间共享此类值的方式,而不必显式地通过组件树的逐层传递 props。
使用 context, 可以避免通过中间元素传递 props:
// Context 可以让我们无须明确地传遍每一个组件,就能将值深入传递进组件树。
// 为当前的 theme 创建一个 context(“light”为默认值)。
const ThemeContext = React.createContext('light');
class App extends React.Component {
render() {
// 使用一个 Provider 来将当前的 theme 传递给以下的组件树。
// 无论多深,任何组件都能读取这个值。
// 在这个例子中,我们将 “dark” 作为当前的值传递下去。
return (
<ThemeContext.Provider value="dark">
<Toolbar />
</ThemeContext.Provider>
);
}
}
// 中间的组件再也不必指明往下传递 theme 了。
function Toolbar() {
return (
<div>
<ThemedButton />
</div>
);
}
class ThemedButton extends React.Component {
// 指定 contextType 读取当前的 theme context。
// React 会往上找到最近的 theme Provider,然后使用它的值。
// 在这个例子中,当前的 theme 值为 “dark”。
static contextType = ThemeContext;
render() {
return <Button theme={this.context} />;
}
}
子组件向父组件传递事件
函数组件
也就是实现在父组件中调用子组件实例方法
你应该熟悉 ref这一种访问 DOM 的主要方式
ref 就像是鱼竿加鱼线 ,你是父组件,鱼是子组件,通过鱼线你可以对鱼为所欲为
子组件:
useRef返回一个可变的 ref 对象,其 .current属性被初始化为传入的参数(initialValue)。
返回的ref对象在组件的整个生命周期内持续存在。
useImperativeHandle可以让你在使用ref时自定义暴露给父组件的实例值。
在子组件中使用useImperativeHandle 向父组件暴露 focus和 onClick方法
const Child = (props, ref) => {
// 子组件中创建 ref 实现对input 输入框的访问
const inputRef = useRef()
const focusFun = () => { inputRef.current.focus() }
const onClick = () => { }
// 该 ref 是父组件转发来的的ref
useImperativeHandle(ref, () => ({
focus: focusFun,
onClick: onClick
}));
return <input ref={inputRef} />
}
父组件:
React.forwardRef会创建一个React组件,这个组件能够将其接受的ref属性转发到其组件树下的另一个组件中
父组件调用被forwardRef包裹的组件,并将ref传递给它。
const MyChild = forwardRef(Child)
const Parent = () => {
// 父组件中创建 ref 实现对子组件Child 的访问(父组件中的鱼竿)
const ref = useRef()
console.log(ref)
// 鱼竿勾住子组件
return <MyChild ref={ref}/>
}
打印结果:
class 组件与函数组件类似
此外也可以借助一些第三方库来实现