useState
useMemo
useReducer
useState
const lastStates = []let index = 0function useState(initialState) {lastStates[index] = lastStates[index] || initialStateconst currentIndex = indexfunction setState(nextState) {lastStates[currentIndex] = nextState// render()}return [lastStates[index++], setState]}
useCallback
import { isChanged } from './utils'let lastCallbacklet lastDependenciesfunction useCallback(callback, dependencies) {if (lastDependencies) {if (isChanged(lastDependencies, dependencies)) { // 依赖项改变了, 返回新的callbacklastCallback = callbacklastDependencies = dependencies}} else { // 没有依赖项, 每次返回新的callbacklastCallback = callbacklastDependencies = dependencies}return lastCallback}// export function isChanged(lastDeps, deps) {// const changed = !lastDeps.every((dep, idx) => {// return dep === deps[idx]// })// return changed// }
useMemo
import { isChanged } from './utils'let lastMemolet lastDependenciesfunction useMemo(callback, dependencies) {if (lastDependencies) {if (isChanged(lastDependencies, dependencies)) {lastMemo = callback()lastDependencies = dependencies}} else {lastMemo = callback()lastDependencies = dependencies}}
useReducer
let lastStatefunction useReducer(reducer, initialState) {lastState = lastState || initialStateconst dispatch = (action) => {lastState = reducer(lastState, action)// render()}return [lastState, dispatch]}// useageconst reducer = (state, action) => {switch(action.type) {case 'add':return state + 1default:return state}}cosnt [state, dispatch] = useReducer(reducer, 0)
useContext
function useContext(context) {return context._currentValue}
useEffect
import { isChanged } from './utils'let lastDependencies// callback在浏览器渲染完成之后执行function useEffect(callback, dependencies) {if (lastDependencies) {if (isChanged(lastDependencies, dependencies)) { // 依赖项改变了, 返回新的callbacksetTimeout(callback, 0)lastDependencies = dependencies}} else { // 没有依赖项, 每次返回新的callbacksetTimeout(callback, 0)lastDependencies = dependencies}return lastCallback}
useLayoutEffect
import { isChanged } from './utils'let lastDependencies// callback在render之后,浏览器渲染之前执行function useLayoutEffect(callback, dependencies) {if (lastDependencies) {if (isChanged(lastDependencies, dependencies)) { // 依赖项改变了, 返回新的callbackPromise.resolve().then(callback)// 或者// queueMicrotask(callback)lastDependencies = dependencies}} else { // 没有依赖项, 每次返回新的callbackPromise.resolve().then(callback)// 或者// queueMicrotask(callback)lastDependencies = dependencies}return lastCallback}
useRef
let lastReffunction useRef(initialRef) {lastRef = lastRef || initialRefreturn {current: lastRef}}
