從Vue.js源碼中我學到的幾個實用函數

大家好,我是若川。歡迎加我微信?ruochuan12,長期交流學習。今天推薦Vuejs源碼中幾個實用的方法。

如果想看Vuejs源碼,不知道如何下手,一般推薦配置Sourcemap,針對單個問題調試來看,如何調試Vuejs源碼,我的vuex源碼文章中寫了。

點擊下方卡片關注我、加個星標,或者查看源碼等系列文章。學習源碼整體架構系列、年度總結、JS基礎系列


話不多說,趕快試試尤大大教給我們的這幾個實用函數吧!在工作中肯定會用得到。

立即執行函數

頁面加載完成后只執行一次的設置函數。

(function?(a,?b)?{console.log(a,?b);?//?1,2
})(1,?2);

通常,全局變量被作為一個參數傳遞給立即執行參數,這樣它在函數內部不使用window也可以被訪問到。

(function?(global)?{console.log(global);?//?Window對象
})(this);

多層嵌套三目運算符

三目運算符嵌套的寫法,使得代碼可讀性差,簡單業務場景下可以試著使用。

var?a?=?1;
var?b?=?0;
a?==?1???(b?==?2???(b?=?3)?:?(b?=?1))?:?"";
console.log(b);?//?1

凍結對象

不可對指定對象增刪改。

var?emptyObject?=?Object.freeze({key:?"1",
});
emptyObject.name?=?"maomin";
delete?emptyObject.key;
emptyObject.key?=?"2";
console.log(emptyObject);

密封對象

只能對指定對象進行更改,不可進行增加刪除操作。

var?sealObject?=?Object.seal({key:?3,
});
sealObject.name?=?"maomin";
delete?sealObject.key;
sealObject.key?=?4;
console.log(sealObject);?//?4

檢查是否是原始值

function?isPrimitive(value)?{return?(typeof?value?===?"string"?||typeof?value?===?"number"?||//?$flow-disable-linetypeof?value?===?"symbol"?||typeof?value?===?"boolean");
}

快速檢測是否是對象

當我們知道原始值時,它主要用于將對象與原始值區分開來。

function?isObject(obj)?{return?obj?!==?null?&&?typeof?obj?===?"object";
}
console.log(isObject(true));?//false

檢測目標類型

var?_toString?=?Object.prototype.toString;function?toRawType(value)?{return?_toString.call(value).slice(8,?-1);
}
console.log(toRawType([]));?//?Array

檢查目標是否是有效的數組索引

function?isValidArrayIndex(val)?{var?n?=?parseFloat(String(val));return?n?>=?0?&&?Math.floor(n)?===?n?&&?isFinite(val);
}

檢測是否是Promise對象

function?isDef(v)?{return?v?!==?undefined?&&?v?!==?null;
}
function?isPromise(val)?{return?(isDef(val)?&&typeof?val.then?===?"function"?&&typeof?val.catch?===?"function");
}
var?promiseObj?=?new?Promise(function?(resolve,?reject)?{//?一段耗時的異步操作resolve("成功");?//?數據處理完成//?reject('失敗')?//?數據處理出錯
}).then((res)?=>?{console.log(res);},?//?成功(err)?=>?{console.log(err);}?//?失敗
);
console.log(isPromise(promiseObj));?//?true

目標轉換為字符串

var?_toString?=?Object.prototype.toString;
function?isPlainObject(obj)?{return?_toString.call(obj)?===?"[object?Object]";
}
function?toString(val)?{return?val?==?null??"":?Array.isArray(val)?||?(isPlainObject(val)?&&?val.toString?===?_toString)??JSON.stringify(val,?null,?2):?String(val);
}
console.log(toString({?name:?1?}));?//?{"name":?1}

轉化為數字

將輸入值轉換為數字以便持久化。如果轉換失敗,則返回原始字符串。

function?toNumber(val)?{var?n?=?parseFloat(val);return?isNaN(n)???val?:?n;
}

檢測key是否在創建的Map對象內

function?makeMap(str,?expectsLowerCase)?{var?map?=?Object.create(null);var?list?=?str.split(",");for?(var?i?=?0;?i?<?list.length;?i++)?{map[list[i]]?=?true;}return?expectsLowerCase??function?(val)?{return?map[val.toLowerCase()];}:?function?(val)?{return?map[val];};
}
var?isBuiltInTag?=?makeMap("slot,component",?true);
console.log(isBuiltInTag("component"));?//?true

刪除簡單數組中某一項

function?remove(arr,?item)?{if?(arr.length)?{var?index?=?arr.indexOf(item);if?(index?>?-1)?{return?arr.splice(index,?1);}}
}
console.log(remove([1,?2],?1));?//?[1]

檢測對象中是否有指定key

var?hasOwnProperty?=?Object.prototype.hasOwnProperty;
function?hasOwn(obj,?key)?{return?hasOwnProperty.call(obj,?key);
}
console.log(hasOwn({?name:?1?},?"name"));?//true

將類數組對象轉化為真實數組

function?toArray(list,?start)?{start?=?start?||?0;var?i?=?list.length?-?start;var?ret?=?new?Array(i);while?(i--)?{ret[i]?=?list[i?+?start];}return?ret;
}
console.log(toArray({?0:?42,?1:?52,?2:?63,?length:?3?}));?//?[42,?52,?63]

將屬性混合到目標對象中

function?extend(to,?_from)?{for?(var?key?in?_from)?{to[key]?=?_from[key];}return?to;
}
console.log(extend({?name:?1?},?{?name1:?2?}));?//?{name:1,name1:2}

將對象數組合并為單個對象

function?extend(to,?_from)?{for?(var?key?in?_from)?{to[key]?=?_from[key];}return?to;
}
function?toObject(arr)?{var?res?=?{};for?(var?i?=?0;?i?<?arr.length;?i++)?{if?(arr[i])?{extend(res,?arr[i]);}}return?res;
}
console.log(toObject([{?name:?1?},?{?name:?1?},?{?name:?2?},?{?name1:?3?}]));?//?{name:?2,?name1:?3}

檢測指定項在數組(簡單數組、數組對象)中的索引

function?isObject(obj)?{return?obj?!==?null?&&?typeof?obj?===?"object";
}
function?looseEqual(a,?b)?{if?(a?===?b)?{return?true;}var?isObjectA?=?isObject(a);var?isObjectB?=?isObject(b);if?(isObjectA?&&?isObjectB)?{try?{var?isArrayA?=?Array.isArray(a);var?isArrayB?=?Array.isArray(b);if?(isArrayA?&&?isArrayB)?{return?(a.length?===?b.length?&&a.every(function?(e,?i)?{return?looseEqual(e,?b[i]);}));}?else?if?(a?instanceof?Date?&&?b?instanceof?Date)?{return?a.getTime()?===?b.getTime();}?else?if?(!isArrayA?&&?!isArrayB)?{var?keysA?=?Object.keys(a);var?keysB?=?Object.keys(b);return?(keysA.length?===?keysB.length?&&keysA.every(function?(key)?{return?looseEqual(a[key],?b[key]);}));}?else?{/*?istanbul?ignore?next?*/return?false;}}?catch?(e)?{/*?istanbul?ignore?next?*/return?false;}}?else?if?(!isObjectA?&&?!isObjectB)?{return?String(a)?===?String(b);}?else?{return?false;}
}function?looseIndexOf(arr,?val)?{for?(var?i?=?0;?i?<?arr.length;?i++)?{if?(looseEqual(arr[i],?val))?{return?i;}}return?-1;
}
console.log(looseIndexOf([{?name:?1?},?{?name:?2?}],?4));?//?-1
console.log(looseIndexOf([{?name:?1?},?{?name:?2?}],?{?name:?1?}));?//?0

確保函數只調用一次

function?once(fn)?{var?called?=?false;return?function?()?{if?(!called)?{called?=?true;fn.apply(this,?arguments);}};
}
var?callOnce?=?once(function?()?{console.log("javascript");
});
callOnce();?//?javascript
callOnce();

定義對象屬性

如果你想禁止一個對象添加新屬性并且保留已有屬性,就可以使用Object.preventExtensions(obj)。

function?def(obj,?key,?val,?enumerable)?{Object.defineProperty(obj,?key,?{value:?val,?//?對象定義屬性enumerable:?!!enumerable,?//?描述屬性是否會出現在for?in?或者?Object.keys()的遍歷中writable:?true,?//?是否可寫configurable:?true,?//?是否重新定義或者刪除});
}
var?obj?=?{name:?1,
};
def(obj,?"name1",?2,?true);
obj.name1?=?3;
console.log(obj);?//?{name:?1,?name1:?3}

瀏覽器環境嗅探

var?inBrowser?=?typeof?window?!==?"undefined";
var?inWeex?=?typeof?WXEnvironment?!==?"undefined"?&&?!!WXEnvironment.platform;
var?weexPlatform?=?inWeex?&&?WXEnvironment.platform.toLowerCase();
var?UA?=?inBrowser?&&?window.navigator.userAgent.toLowerCase();var?isIE?=?UA?&&?/msie|trident/.test(UA);
var?isIE9?=?UA?&&?UA.indexOf("msie?9.0")?>?0;
var?isEdge?=?UA?&&?UA.indexOf("edge/")?>?0;
var?isAndroid?=?(UA?&&?UA.indexOf("android")?>?0)?||?weexPlatform?===?"android";
var?isIOS?=?(UA?&&?/iphone|ipad|ipod|ios/.test(UA))?||?weexPlatform?===?"ios";
var?isChrome?=?UA?&&?/chrome\/\d+/.test(UA)?&&?!isEdge;
var?isPhantomJS?=?UA?&&?/phantomjs/.test(UA);
var?isFF?=?UA?&&?UA.match(/firefox\/(\d+)/);

JS構造函數內的方法與構造函數prototype屬性上方法的對比

定義在構造函數內部的方法,會在它的每一個實例上都克隆這個方法;定義在構造函數的 prototype 屬性上的方法會讓它的所有示例都共享這個方法,但是不會在每個實例的內部重新定義這個方法。如果我們的應用需要創建很多新的對象,并且這些對象還有許多的方法,為了節省內存,我們建議把這些方法都定義在構造函數的 prototype 屬性上。當然,在某些情況下,我們需要將某些方法定義在構造函數中,這種情況一般是因為我們需要訪問構造函數內部的私有變量。

function?A()?{this.say?=?function?()?{console.log(1);};
}
var?a?=?new?A();
a.say();
function?B()?{}
B.prototype.say?=?function?()?{console.log(2);
};
var?b?=?new?B();
b.say();
var?c?=?new?B();
c.say();

獲取標簽內容(包含標簽)

function?getOuterHTML(el)?{if?(el.outerHTML)?{return?el.outerHTML;}?else?{var?container?=?document.createElement("div");container.appendChild(el.cloneNode(true));return?container.innerHTML;}
}

字符串hash值

function?hash(str)?{var?hash?=?5381;var?i?=?str.length;while?(i)?{hash?=?(hash?*?33)?^?str.charCodeAt(--i);}return?hash?>>>?0;
}
console.log(hash("222sd"));//?164533792

最近組建了一個江西人的前端交流群,如果你也是江西人可以加我微信 ruochuan12 拉你進群。


·················?若川出品?·················

今日話題

有時候付費學習,真的是能節省很多時間,時間也是資源,也是金錢。視頻學習和書籍學習都是很好的學習方式,相輔相成,當然,符合自己學習方式才是最重要的。書籍出版一般要經過嚴格審核流程,網上視頻的質量參差不齊。歡迎分享、收藏、點贊、在看我的公眾號文章~

一個愿景是幫助5年內前端人走向前列的公眾號

可加我個人微信 ruochuan12,長期交流學習

推薦閱讀

我在阿里招前端,我該怎么幫你?(現在還能加我進模擬面試群)

如何拿下阿里巴巴 P6 的前端 Offer

點擊方卡片關注我、加個星標,或者查看源碼等系列文章。
學習源碼整體架構系列、年度總結、JS基礎系列

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/275987.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/275987.shtml
英文地址,請注明出處:http://en.pswp.cn/news/275987.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

real類型_如何使用REAL方法對您的Web內容進行現實檢查

real類型Web內容審核模板 (Web content audit template) I recently completed a website audit project for a nonprofit organization through CatchAFire.org. As part of the website audit, I audited every key page’s content, looking for areas of opportunity.我最近…

青海行--(7月26日)翻越祁連山

嘉峪關是最值得一寫的&#xff0c;雖然也是著名的旅游城嘉峪關景點是國家&#xff21;&#xff21;&#xff21;&#xff21;&#xff21;級景區&#xff0c;但與敦煌完全不一樣&#xff0c;沒有人山人海的游客&#xff0c;門票也不貴&#xff0c;才&#xff11;&#xff10;&a…

TikTok真題第1天 | 666.路徑和IV、 207.課程表、210.課程表||

666.路徑和IV 題目鏈接&#xff1a;666.路徑和IV 解法&#xff1a; 參考這篇題解&#xff1a;【LeetCode - 666】路徑和 IV_力扣666路徑總和4-CSDN博客 關鍵點在于&#xff1a; &#xff08;1&#xff09;使用map來存node&#xff1a;key 為整數的前兩位&#xff0c;value…

導出Excel

2019獨角獸企業重金招聘Python工程師標準>>> 思路: 1, 引入Excel類庫; 2, 創建一個模板; 3, 將數據填充進去; 4, 生成文件; 下面是一個簡單的示例 $phpExcelObj new PHPExcel(); $titleMap self::TITLE_MAP; //設置表頭 $i 0; foreach ($titleMap as $key > $…

CentOS系統更換yum源(repomd.xml not found解決方案)

CentOS系統更換yum源 問題 當初瞎鼓搗服務器&#xff0c;更換yum源為aliyun的&#xff0c;奈何阿里的源最近全部打不開&#xff0c;導致yum安裝不了&#xff0c;一直報錯&#xff1a; http://mirrors.aliyun.com/centos/6/os/x86_64/repodata/repomd.xml: [Errno 14] PYCURL E…

在類中用class時數據是共有還是私有_jvm學習筆記之class文件的加載、初始化

編寫的java文件在要真正運行時&#xff0c;會首先被編譯成 “.class"結尾的二進制文件&#xff0c;然后被虛擬機加載。那么在虛擬機中一個class文件要成為java實例&#xff0c;需要經歷好幾個步驟&#xff1a;1、裝載&#xff1a;裝載階段由三個基本動作完成&#xff0c;要…

所有前端都要看的2D游戲化互動入門基礎知識

背景現在越來越多的公司和APP開始使用游戲化的方式去做產品了&#xff0c;所謂游戲化&#xff0c;是指在非游戲環境中將游戲的思維和游戲的機制進行整合運用&#xff0c;以引導用戶互動和使用的方法。支付寶里面的螞蟻莊園、螞蟻森林&#xff0c;通過游戲和公益的結合實現用戶的…

江蘇一動物園現“旋轉活馬” 園方:創意來自馬術訓練

中新網南通1月31日電 (記者唐娟)“旋轉馬設備采用同時容納六匹馬的遛馬器組裝而成&#xff0c;對馬匹沒有任何傷害&#xff0c;初衷是希望給小朋友一種全新體驗&#xff0c;這才有了這個創意項目。”1月31日&#xff0c;針對活馬版“旋轉木馬”引發的熱議&#xff0c;江蘇南通森…

Byte數組轉換成string 的方法積累

.net的加密算法&#xff0c;返回的都是byte[] 類型&#xff0c;在存貯起來讓人非常頭疼&#xff0c;最簡單的方法就是把byte[]轉換成string來存貯&#xff0c;當然如果數據量大的話&#xff0c;另當別論。 所以我就把byte[]轉換成string的方法做一個簡單的積累與分析。目前有3種…

加快信息化建設對地方發展的_加快設計師職業發展的9種方法

加快信息化建設對地方發展的重點 (Top highlight)Over the past few months, I have had an increase in conversations with design students from various institutions, as well as early, to senior-level designers, researchers, & product managers from various co…

Docker:Nginx-Redis-Mysql-PHP 部署

Docker:Nginx-Redis-Mysql-PHP 部署 網絡橋接 Docker容器之間默認網絡隔離&#xff0c;需要使用橋接網絡進行互通 創建網絡 docker network create net-local docker network ls NETWORK ID NAME DRIVER SCOPE da9c8fc3dc80 bridge bridge local 78641…

epoll監聽文件_介紹一下 Android Handler 中的 epoll 機制?

介紹一下 Android Handler 中的 epoll 機制&#xff1f;目錄&#xff1a;IO 多路復用select、poll、epoll 對比epoll APIepoll 使用示例Handler 中的 epoll 源碼分析IO 多路復用IO 多路復用是一種同步 IO 模型&#xff0c;實現一個線程可以監視多個文件句柄。一旦某個文件句柄就…

前端工程師的一大神器——puppeteer

大家好&#xff0c;我是若川。歡迎加我微信 ruochuan12&#xff0c;長期交流學習。今天推薦神器puppeteer&#xff0c;我猜有挺多人不知道。文章不長&#xff0c;看完有空也可以試玩。我18年也寫過一篇puppeteer爬取生成pdf的文章&#xff0c;時間真快。前端使用puppeteer 爬蟲…

selenium界面元素定位

一、 Selenium界面元素定位 本文元素定位以das2為例 #導入包 from selenium import webdriver #打開火狐驅動 driverwebdriver.Firefox() #訪問網址 driver.get("http://192.168.3.217:8080/das/seatlogin.jsp ") 進行web頁面自動化測試&#xff0c;對頁面上…

vue.js ui_UI / UX開發:考慮Vue.js

vue.js uiBecause sometimes we have to add logic to our concepts, and Vue makes it a whole lot easier.因為有時我們必須在概念中添加邏輯&#xff0c;而Vue使其變得更加容易。 FULL DISCLOSURE: THIS IS NOT A COMPLETE JAVASCRIPT OR VUE COURSE. There’s no way I co…

Silverlight學習筆記十七BingMap(三)之地圖的地區標識

如果我們需要在Bing Maps中加入一個小圖釘標記&#xff0c;該如何實現了&#xff1f; Bing Maps控件已經為我們提供了這個功能&#xff0c;在Microsoft.Maps.MapControl名稱空間下提供了實現圖釘應用的圖釘層Pushpin類用該類來實現普通標識 在Xaml中添加<map:Pushpin Locati…

win10查看pcie設備_壹拓網科技解密WIN10系統使用向日葵開機棒遠程開機需要設置幾個地方...

向日葵開機棒&#xff0c;是一款非常好用的遠程智能遠程開機硬件&#xff0c;它一頭接網線&#xff0c;另外一頭和被開電腦接在同一個路由器下&#xff0c;不需要和被開電腦或者設備直接連接&#xff0c;當然&#xff0c;被開電腦需要有線聯網&#xff0c;暫時不支持使用無線方…

如何成為公司獨當一面的工程師

大家好&#xff0c;我是若川。歡迎加我微信 ruochuan12&#xff0c;長期交流學習。今天推薦黃老師的這篇文章&#xff0c;你可能看到過了&#xff0c;但值得再看一遍。之前常有小伙伴問&#xff0c;大多情況下我都會分享這篇文章。點擊下方卡片關注我、加個星標&#xff0c;或者…

webpack4.0配置記錄(2)

接上一篇webpack4.0配置記錄(1),繼續記錄學習webpack配置。 定義環境變量 new Webpack.DefinePlugin({//用來定義全局環境變量DEV:JSON.stringify(dev),FLAG:true }), webpack簡單優化 noParsemodule:{noParse:/jquery/,//不去解析設置的包所依賴的關系,如jquery } ignorePlugi…

flex如何做響應式設計_響應式設計-您做錯了!

flex如何做響應式設計Responsive design is not just about the web that automatically adjusts to different screen resolutions and resizeable images, but designs that are crucial for web performance.自適應設計不僅涉及可自動適應不同屏幕分辨率和可調整大小圖像的網…