最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

react?源碼中位運(yùn)算符的使用詳解

 更新時(shí)間:2022年03月07日 16:32:43   作者:神奇大叔  
這篇文章主要為大家詳細(xì)介紹了react?位運(yùn)算符,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下,希望能夠給你帶來(lái)幫助

位運(yùn)算符基本使用

  • 按位與(&):a & b對(duì)于每一個(gè)比特位,兩個(gè)操作數(shù)都為 1 時(shí), 結(jié)果為 1, 否則為 0
  • 按位或(|):a | b對(duì)于每一個(gè)比特位,兩個(gè)操作數(shù)都為 0 時(shí), 結(jié)果為 0, 否則為 1
  • 按位異或(^):a ^ b對(duì)于每一個(gè)比特位,兩個(gè)操作數(shù)相同時(shí), 結(jié)果為 1, 否則為 0
  • 按位非(~):~ a反轉(zhuǎn)操作數(shù)的比特位, 即 0 變成 1, 1 變成 0
0000 0000 0000 0000 0000 0000 0000 0011     -> 3
1111 1111 1111 1111 1111 1111 1111 1100     -> ~ 3 = -4

左移位<<:各二進(jìn)位全部左移若干位,高位丟棄,低位補(bǔ)0。

0000 0000 0000 0000 0000 0000 0000 0110     -> 6
0000 0000 0000 0000 0000 0000 0001 1000     -> 6 << 2 = 24

右移位>>:各二進(jìn)位全部右移若干位,正數(shù)高位補(bǔ)0,負(fù)數(shù)高位補(bǔ)1,低位丟棄

0000 0000 0000 0000 0000 0000 0000 1100     -> 12
0000 0000 0000 0000 0000 0000 0000 0011     -> 12 >> 2 = 3
負(fù)數(shù)情況:
1111 1111 1111 1111 1111 1111 1111 0100    -> -12
1111 1111 1111 1111 1111 1111 1111 1101    -> -12 >> 2 = -3

無(wú)符號(hào)右移位>>>:各二進(jìn)位全部右移若干位,高位補(bǔ)0,低位丟棄。

0000 0000 0000 0000 0000 0000 0000 1100     -> 12
0000 0000 0000 0000 0000 0000 0000 0011     -> 12 >>> 2 = 3
1111 1111 1111 1111 1111 1111 1111 0100    -> -12
0011 1111 1111 1111 1111 1111 1111 1101    -> -12 >> 2 = 1073741821

正數(shù)計(jì)算負(fù)數(shù):

取反后+1

+5:0101
-5:取反1010 最低位+1 = 1011,1011即為二進(jìn)制的-5

負(fù)數(shù)倒推正數(shù):同樣為取反后+1

在js中位運(yùn)算的特點(diǎn)

  • 位運(yùn)算只能在整型變量之間進(jìn)行運(yùn)算
  • js 中的Number類型在底層都是以浮點(diǎn)數(shù)(參考 IEEE754 標(biāo)準(zhǔn))進(jìn)行存儲(chǔ).
  • js 中所有的按位操作符的操作數(shù)都會(huì)被轉(zhuǎn)成補(bǔ)碼(two’s complement)形式的有符號(hào)32位整數(shù)
  • 操作數(shù)為浮點(diǎn)型時(shí),轉(zhuǎn)換流程: 浮點(diǎn)數(shù) -> 整數(shù)(丟棄小數(shù)位) -> 位運(yùn)算
  • 操作數(shù)的大小超過(guò)Int32范圍(-2^31 ~ 2^31-1). 超過(guò)范圍的二進(jìn)制位會(huì)被截?cái)? 取低位32bit
  • 另外由于 js 語(yǔ)言的隱式轉(zhuǎn)換, 對(duì)非Number類型使用位運(yùn)算操作符時(shí)會(huì)隱式會(huì)發(fā)生隱式轉(zhuǎn)換, 相當(dāng)于先使用Number(xxx)將其轉(zhuǎn)換為number類型, 再進(jìn)行位運(yùn)算:
'str' >>> 0; //  ===> Number('str') >>> 0  ===> NaN >>> 0 = 0

位掩碼

通過(guò)位移定義的一組枚舉常量, 可以利用位掩碼的特性, 快速操作這些枚舉產(chǎn)量(增加, 刪除, 比較)

const A = 1 << 0; // 0b00000001
const B = 1 << 1; // 0b00000010
const C = 1 << 2; // 0b00000100
屬性增加|
ABC = A | B | C //0b00000111
屬性刪除& ~
AB = ABC & ~C //0b00000011
屬性比較
AB 當(dāng)中包含 B: AB & B === B。// AB & B =>0b00000010 ===B,true
AB 當(dāng)中不包含 C: AB & C === 0 // AB & C =>0b00000000 === 0,true

react中的位運(yùn)算

  • react在涉及狀態(tài)、標(biāo)記位、優(yōu)先級(jí)操作的地方大量使用了位運(yùn)算

標(biāo)記狀態(tài)

  • react源碼內(nèi)部有多個(gè)上下文環(huán)境,在執(zhí)行函數(shù)時(shí)經(jīng)常需要判斷當(dāng)前處在哪個(gè)上下文環(huán)境中
// A上下文
const A = 1; //0001
// B上下文
const B = 2; //0010
// 當(dāng)前所處上下文
let curContext = 0;
// 沒(méi)有處在上下文的標(biāo)志
const NoContext = 0;
假設(shè)進(jìn)入A的上下文
curContext |= A; //即curContext=curContext|A =>0001

判斷是否處在某一上下文中,結(jié)合按位與操作與NoContext
// 是否處在A上下文中,這里為true
(curContext & A) !== NoContext //curContext & A)=>0001 !==0000,所以為true,表示在A的上下文中
// 是否處在B上下文中,這里為false,和上方同理
(curContext & B) !== NoContext 
離開上下文,取出標(biāo)記進(jìn)行恢復(fù)
// 從當(dāng)前上下文中移除上下文A
curContext &= ~A; //curContext=curContext& ~A,即0001&1110=0000,進(jìn)行恢復(fù)
// 是否處在A上下文中,此處為false
(curContext & A) !== NoContext //(curContext & A)為0000 

ReactFiberLane.js

  • 優(yōu)先級(jí)定義
  • 源碼中變量只列出了 31 位, 由于 js 中位運(yùn)算都會(huì)轉(zhuǎn)換成Int32(上文已經(jīng)解釋), 最多為 32 位, 且最高位是符號(hào)位. 所以除去符號(hào)位, 最多只有 31 位可以參與運(yùn)算
//類型定義
export opaque type Lanes = number;
export opaque type Lane = number;
// 變量定義
export const NoLanes: Lanes = /*                        */ 0b0000000000000000000000000000000;
export const NoLane: Lane = /*                          */ 0b0000000000000000000000000000000;
export const SyncLane: Lane = /*                        */ 0b0000000000000000000000000000001;
export const SyncBatchedLane: Lane = /*                 */ 0b0000000000000000000000000000010;
export const InputDiscreteHydrationLane: Lane = /*      */ 0b0000000000000000000000000000100;
const InputDiscreteLanes: Lanes = /*                    */ 0b0000000000000000000000000011000;
const InputContinuousHydrationLane: Lane = /*           */ 0b0000000000000000000000000100000;
const InputContinuousLanes: Lanes = /*                  */ 0b0000000000000000000000011000000;
// ...
// ...
const NonIdleLanes = /*                                 */ 0b0000111111111111111111111111111;
export const IdleHydrationLane: Lane = /*               */ 0b0001000000000000000000000000000;
const IdleLanes: Lanes = /*                             */ 0b0110000000000000000000000000000;
export const OffscreenLane: Lane = /*                   */ 0b1000000000000000000000000000000;

getHighestPriorityLanes

function getHighestPriorityLanes(lanes: Lanes | Lane): Lanes {
  // 判斷 lanes中是否包含 SyncLane
  if ((SyncLane & lanes) !== NoLanes) {
    return_highestLanePriority = SyncLanePriority;
    return SyncLane;
  }
  // 判斷 lanes中是否包含 SyncBatchedLane
  if ((SyncBatchedLane & lanes) !== NoLanes) {
    return_highestLanePriority = SyncBatchedLanePriority;
    return SyncBatchedLane;
  }
  // ...
  // ... 省略其他代碼
  return lanes;
}

getHighestPriorityLane

  • react中處在越低bit位的更新優(yōu)先級(jí)越高(越需要優(yōu)先處理)
  • 分離出最高優(yōu)先級(jí)
  • -lanes:表示負(fù)數(shù)的操作,即先取反然后+1
0b000 0000 0000 0000 0000 0000 0001 0001
function getHighestPriorityLane(lanes) {
  return lanes & -lanes;
}
-lanse:
lanes  0001 0001
~lanes 1110 1110 // 第一步
+1     1110 1111 // 第二步
  0001 0001 // lanes  
& 1110 1111 // -lanes
-----------
  0000 0001
若lanes為0001 0000
  0001 0000 // lanes  
& 1111 0000 // -lanes
-----------
  0001 0000

getLowestPriorityLane

  • 假設(shè) lanes(InputDiscreteLanes) = 0b0000000000000000000000000011000
  • 那么 clz32(lanes) = 27, 由于 InputDiscreteLanes 在源碼中被書寫成了 31 位, 雖然在字面上前導(dǎo) 0 是 26 個(gè), 但是轉(zhuǎn)成標(biāo)準(zhǔn) 32 位后是 27 個(gè)
  • index = 31 - clz32(lanes) = 4
  • 最后 1 << index = 0b0000000000000000000000000010000
  • 相比最初的 InputDiscreteLanes, 分離出來(lái)了最左邊的1
  • 通過(guò) lanes 的定義, 數(shù)字越小的優(yōu)先級(jí)越高, 所以此方法可以獲取最低優(yōu)先級(jí)的 lane
function getLowestPriorityLane(lanes: Lanes): Lane {
  // This finds the most significant non-zero bit.
  const index = 31 - clz32(lanes);
  return index < 0 ? NoLanes : 1 << index;
}

react-reconciler上下文定義

export const NoContext = /*             */ 0b0000000;
const BatchedContext = /*               */ 0b0000001;
const EventContext = /*                 */ 0b0000010;
const DiscreteEventContext = /*         */ 0b0000100;
const LegacyUnbatchedContext = /*       */ 0b0001000;
const RenderContext = /*                */ 0b0010000;
const CommitContext = /*                */ 0b0100000;
export const RetryAfterError = /*       */ 0b1000000;
// ...
// Describes where we are in the React execution stack
let executionContext: ExecutionContext = NoContext;

scheduleUpdateOnFiber

// scheduleUpdateOnFiber函數(shù)中包含了好多關(guān)于executionContext的判斷(都是使用位運(yùn)算)
export function scheduleUpdateOnFiber(
  fiber: Fiber,
  lane: Lane,
  eventTime: number,
) {
  if (root === workInProgressRoot) {
    // 判斷: executionContext 不包含 RenderContext
    if (
      deferRenderPhaseUpdateToNextBatch ||
      (executionContext & RenderContext) === NoContext
    ) {
      // ...
    }
  }
  if (lane === SyncLane) {
    if (
      // 判斷: executionContext 包含 LegacyUnbatchedContext
      (executionContext & LegacyUnbatchedContext) !== NoContext &&
      // 判斷: executionContext 不包含 RenderContext或CommitContext
      (executionContext & (RenderContext | CommitContext)) === NoContext
    ) {
      // ...
    }
  }
  // ...
}
  • 在特定的情況下, 使用位運(yùn)算不僅是提高運(yùn)算速度, 且位掩碼能簡(jiǎn)潔和清晰地表示出二進(jìn)制變量之間的關(guān)系.
  • 但是缺點(diǎn)也很明顯, 不夠直觀, 擴(kuò)展性不好(在 js 當(dāng)中的二進(jìn)制變量, 除去符號(hào)位, 最多只能使用 31 位, 當(dāng)變量的數(shù)量超過(guò) 31 個(gè)就需要組合, 此時(shí)就會(huì)變得復(fù)雜)

總結(jié)

本篇文章就到這里了,希望能夠給你帶來(lái)幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容! 

相關(guān)文章

  • React源碼分析之useCallback與useMemo及useContext詳解

    React源碼分析之useCallback與useMemo及useContext詳解

    這篇文章主要介紹了React useCallback與useMemo及useContext源碼分析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)吧
    2022-11-11
  • 一文帶你了解React中的并發(fā)機(jī)制

    一文帶你了解React中的并發(fā)機(jī)制

    React 18.2.0 引入了一系列并發(fā)機(jī)制的新特性,旨在幫助各位開發(fā)者更好地控制和優(yōu)化應(yīng)用程序的性能和用戶體驗(yàn),下面我們就來(lái)看看如何利用這些新特性構(gòu)建更高效、更響應(yīng)式的應(yīng)用程序吧
    2024-03-03
  • 解析react?函數(shù)組件輸入卡頓問(wèn)題?usecallback?react.memo

    解析react?函數(shù)組件輸入卡頓問(wèn)題?usecallback?react.memo

    useMemo是一個(gè)react hook,我們可以使用它在組件中包裝函數(shù)??梢允褂盟鼇?lái)確保該函數(shù)中的值僅在依賴項(xiàng)之一發(fā)生變化時(shí)才重新計(jì)算,這篇文章主要介紹了react?函數(shù)組件輸入卡頓問(wèn)題?usecallback?react.memo,需要的朋友可以參考下
    2022-07-07
  • React-redux?中useSelector使用源碼分析

    React-redux?中useSelector使用源碼分析

    在一個(gè) action 被分發(fā)(dispatch) 后,useSelector() 默認(rèn)對(duì) select 函數(shù)的返回值進(jìn)行引用比較 ===,并且僅在返回值改變時(shí)觸發(fā)重渲染,,這篇文章主要介紹了React-redux?中useSelector使用,需要的朋友可以參考下
    2023-10-10
  • React?Hooks項(xiàng)目實(shí)戰(zhàn)

    React?Hooks項(xiàng)目實(shí)戰(zhàn)

    React?Hooks是React?16.8版本引入的新特性,它使得在函數(shù)組件中也能夠使用狀態(tài)(state)和其他React特性,本文就來(lái)詳細(xì)介紹一下React?Hooks項(xiàng)目實(shí)戰(zhàn),感興趣的可以了解一下
    2023-11-11
  • 探討JWT身份校驗(yàn)與React-router無(wú)縫集成

    探討JWT身份校驗(yàn)與React-router無(wú)縫集成

    這篇文章主要為大家介紹了JWT身份校驗(yàn)與React-router無(wú)縫集成的探討解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-06-06
  • 詳解react-navigation6.x路由庫(kù)的基本使用

    詳解react-navigation6.x路由庫(kù)的基本使用

    最近兩個(gè)項(xiàng)目都用到了React Navigation,所以就研究一下如何使用,本文主要介紹了react-navigation6.x路由庫(kù)的基本使用,感興趣的可以了解一下
    2021-11-11
  • 在react中使用 indexDb的方法

    在react中使用 indexDb的方法

    在React中使用IndexedDB進(jìn)行前端離線存儲(chǔ),可以存儲(chǔ)大量數(shù)據(jù),支持復(fù)雜的數(shù)據(jù)類型和高性能查詢,通過(guò)示例展示了如何創(chuàng)建數(shù)據(jù)庫(kù)、添加數(shù)據(jù)、查詢數(shù)據(jù)和構(gòu)建一個(gè)簡(jiǎn)單的待辦事項(xiàng)應(yīng)用,感興趣的朋友跟隨小編一起看看吧
    2024-11-11
  • 淺談React 中的淺比較是如何工作的

    淺談React 中的淺比較是如何工作的

    React 中淺比較的概念無(wú)處不在,它在不同的流程中起著關(guān)鍵的作用,本文主要介紹了React 中的淺比較是如何工作的,具有一定的參考價(jià)值,感興趣的可以了解一下
    2022-04-04
  • 使用React和Redux Toolkit實(shí)現(xiàn)用戶登錄功能

    使用React和Redux Toolkit實(shí)現(xiàn)用戶登錄功能

    在React中,用戶登錄功能是一個(gè)常見的需求,為了實(shí)現(xiàn)該功能,需要對(duì)用戶輸入的用戶名和密碼進(jìn)行驗(yàn)證,并將驗(yàn)證結(jié)果保存到應(yīng)用程序狀態(tài)中,在React中,可以使用Redux Toolkit來(lái)管理應(yīng)用程序狀態(tài),從而實(shí)現(xiàn)用戶登錄功能,需要詳細(xì)了解可以參考下文
    2023-05-05

最新評(píng)論

福泉市| 英吉沙县| 延长县| 乳山市| 镇坪县| 霍邱县| 宜川县| 桃园县| 泰顺县| 萝北县| 宁津县| 梧州市| 平昌县| 普兰县| 城口县| 乌海市| 竹山县| 南召县| 泰顺县| 嵊泗县| 体育| 吴堡县| 巢湖市| 西宁市| 泽库县| 霍山县| 竹山县| 高雄市| 民权县| 阳西县| 桦甸市| 高唐县| 宾阳县| 新闻| 通城县| 甘德县| 任丘市| 岢岚县| 三都| 公主岭市| 灵石县|