JS基礎源碼之手寫模擬new

JS基礎源碼之手寫模擬new

  • 手寫模擬new
    • 初步實現
    • 最終實現

手寫模擬new

new 運算符創建一個用戶定義的對象類型的實例或具有構造函數的內置對象類型之一。
我們先看看new實現了哪些功能:

function Person (name,age){this.name = name;this.age = age;this.habit = 'Games';
}
Person.prototype.strength = 80;
Person.prototype.sayYourName = function (){console.log('I am ', this.name);
}
var person = new Person('kin',18);
console.log(person.name);//kin
console.log(person.habit);//Games
console.log(person.strength);//80
person.sayYourName();// I am kin

我們可以看到,實例person可以:

  1. 訪問到Otaku構造函數里的屬性;
  2. 訪問到Otaku.prototype中的屬性;
    接下來,我們可以嘗試著模擬一下:
    因為new是關鍵字,所以無法像bind函數一樣直接覆蓋,所以我們寫一個函數,命名為objectFactory,來模擬new的效果,用的時候是這樣的:
function Person(){...
}
//使用new
var person = new Person(...);
//使用objectFactory
var person = objectFactory(Person,...)

初步實現

因為new的結果是一個新的對象,所以在模擬實現的時候,我們也要建立一個新對象,假設這個對象叫obj,因為obj會具有Person構造函數里的屬性,我們可以使用Person.apply(obj,arguments)來給obj添加新的屬性。
然后,實例的proto屬性會指向構造函數的prototype,也正是因為建立起這樣的關系,實例可以訪問原型上的屬性。

//第一版代碼
function objectFactory(){var obj = new Object();Constructor = [].shift.call(arguments);obj.__proto__ = Constructor.prototype;Constructor.apply(obj,arguments);return obj;
}

在這一版中,我們:

  1. 用new Object()的方式新建了一個對象obj;
  2. 取出第一個參數,就是我們要傳入的構造函數。此外因為shift會修改原數組,所以arguments會被去除第一個參數;
  3. 將obj的原型指向構造函數,這樣obj就可以訪問到構造函數原型中的屬性;
  4. 使用apply,改變構造函數this的指向到新建的對象,這樣obj就可以訪問到構造函數中的屬性;
  5. 返回obj;
    測試下:
function Person (name,age){this.name = name;this,age = age;this,habit = 'Games';
}
Person.prototype.strength = 88;
Person.prototype.sayYourName = function(){console.log('I am',this.name);
}
function objectFactory(){var obj = new Object();Constructor = [].shift.call(arguments);obj.__proto__ = Constructor.prototype;Constructor.apply(obj,arguments);return obj;
};
var person = objectFactory(Person,'kin',17);
console.log(person.name);//kin
console.log(person.habit);//Games
console.log(person.strength);//88
person.sayYourName();// I am kin

最終實現

假如構造函數有返回值

function Person(name,age){this.strength = 90;this.age = age;return {name:name,habit:'Games'}
}
var person = new Person('kin',12);
console.log(person.name);//kin
console.log(person.habit);//Games
console.log(person.strength);//undefined
console.log(person.age);//undefined

在這個案例中,構造函數返回了一個對象,在實例person中只能訪問返回的對象中的屬性。
而且還要注意一點,在這里我們是返回一個對象,假如我們只是返回一個基本類型的值呢?
我們再看一個例子:

Function Person(name,age){this.strength = 60;this.age = age;return 'handsome boy';
}
var person = new Otaku('kin',12);
console.log(person.name);//undefined
console.log(person.age);//undefined
console.log(person.strength);//60
console.log(person.age);//18

這次盡管有返回值,但是相當于沒有對返回值進行處理。
所以我們還需要判斷返回的值是不是一個對象,如果是一個對象,我們就返回這個對象,如果沒有,我們該返回什么就返回什么。

//最終版的代碼
function objectFactory(){var obj = new Object();Constructor = [].shift.call(arguments);obj.__proto__ = Constructor.apply(obj,arguments);return typeof ret == 'object' ? ret : obj;
};

本文章可以參考JS基礎之原型&原型鏈一起看,學習效果更佳喲~

好啦!簡單的知識點就到這里啦休息一下獎勵自己一下!
在這里插入圖片描述
在這里插入圖片描述
在這里插入圖片描述

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

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

相關文章

開發猿的平平淡淡周末---2023/12/9

上周回顧 完成了遺留的開發任務,基本全部完成進一步了解了系統當時設計的原理熟悉了代碼的重構 2023.12.9 天氣晴 溫度適宜 前言 小伙伴們大家好,時間很快,又來到了周末,也是一個平平淡淡的周末。上周只更了一篇博客...原…

滲透測試 | 滲透測試之信息收集

滲透測試(penetration test,pentest)是實施安全評估(即審計)的具體手段。 滲透測試可能是單獨進行的一項工作,也可能是常規研發生命周期(例如,Microsoft SDLC)里 IT 安全…

Unicode編碼解碼

一、Unicode概述 Unicode是一種字符編碼標準,旨在解決不同字符集之間的兼容性問題。它為全球所有語言提供了一種統一的編碼方式,使得各種字符能夠在計算機系統中正確顯示和處理。Unicode字符集包含了世界上幾乎所有的字符,包括中文字符、英文…

算法Day23 簡單吃飯(0-1背包)

簡單吃飯(0-1背包) Description Input Output Sample 代碼 import java.util.Scanner; public class Main {public static void main(String[] args) {Scanner scanner new Scanner(System.in);int n scanner.nextInt();int total scanner.nextInt(…

WebDriver核心方法和屬性:掌握自動化測試的利器

在自動化測試中,Selenium WebDriver是一個非常重要的工具。它提供了一種方式來模擬用戶與瀏覽器的交互,從而進行各種操作,如點擊按鈕、輸入文本等。本文將介紹WebDriver的核心方法和屬性,以及如何使用它們。 1. 啟動和關閉瀏覽器…

使用es256算法生成jwt

1、使用hutool來做 1、先去jwt解密/加密 - bejson在線工具弄個公私鑰 2、導入hutool maven <dependency><groupId>cn.hutool</groupId><artifactId>hutool-all</artifactId><version>5.7.22</version></dependency><depe…

高項備考葵花寶典-項目進度管理輸入、輸出、工具和技術(中,很詳細考試必過)

項目進度管理的目標是使項目按時完成。有效的進度管理是項目管理成功的關鍵之一&#xff0c;進度問題在項目生命周期內引起的沖突最多。 小型項目中&#xff0c;定義活動、排列活動順序、估算活動持續時間及制定進度模型形成進度計劃等過程的聯系非常密切&#xff0c;可以視為一…

Pytorch中的resize和reshape

torch.reshape() 官方文檔的大致意思是&#xff1a; 返回與輸入具有相同數據和元素數量的張量&#xff0c;但是具有指定形狀。如果可能&#xff0c;返回的張量將是輸入的視圖&#xff0c;也就是說原本的tensor并沒有被改變&#xff0c;如果想要改變那么就將改變的tensor賦值給…

情深不必糾纏

那一年&#xff0c;男孩女孩在萬千人中相遇了。多年后女人的一封郵件&#xff0c;讓男人與女人的靈魂相遇了。他們無緣夫妻&#xff0c;卻發現彼此是靈魂的陪伴。不能攜手相守&#xff0c;卻懂得彼此的心靈。 有一天&#xff0c;女人告訴男人要回家了&#xff0c;問男人心里會不…

ejs —— 三目運算符的用法

EJS&#xff08;Embedded JavaScript&#xff09;是一種簡單的模板語言&#xff0c;它允許將JavaScript代碼嵌入到HTML中。在EJS中&#xff0c;<%、<%和<%-是用于將JavaScript代碼嵌入到模板中的語法。 <%&#xff1a;這是EJS的輸出表達式&#xff0c;用于將變量的…

阿里云安裝docker

文章目錄 一、 yum 進行安裝&#xff08;os版本 CentOS 7&#xff09; 推薦二、 apt-get 進行安裝(os版本 Ubuntu 14.04/16.04&#xff09;三、測試四、阿里云docker加速 一、 yum 進行安裝&#xff08;os版本 CentOS 7&#xff09; 推薦 # step 1: 安裝必要的一些系統工具 su…

<HarmonyOS第一課>應用服務上架【課后考核】

【習題】HarmonyOS應用/元服務上架 判斷題 元服務發布的國家與地區僅限于“中國大陸” 正確(True) 編譯打包的軟件包存放在項目目錄build > outputs > default下 正確(True) 單選題 創建應用時&#xff0c;應用包名需要和app.json5或者config.json文件中哪個字段保持…

VMware安裝Ubuntu20.04并使用Xshell連接虛擬機

文章目錄 虛擬機環境準備重置虛擬網絡適配器屬性&#xff08;可選&#xff09;配置NAT模式的靜態IP創建虛擬機虛擬機安裝配置 Xshell連接虛擬機 虛擬機環境準備 VMware WorkStation Pro 17.5&#xff1a;https://customerconnect.vmware.com/cn/downloads/details?downloadGr…

基于Java旅游信息管理系統

基于Java旅游信息管理系統 功能需求 1、旅游目的地管理&#xff1a;系統需要能夠記錄和管理各個旅游目的地的詳細信息&#xff0c;包括景點介紹、交通方式、住宿推薦等。管理員可以添加、編輯和刪除目的地信息。 2、旅游線路規劃&#xff1a;系統需要提供旅游線路規劃功能&a…

C++類名后面跟大括號和跟小括號的區別

在 C 中&#xff0c;類名后面跟著大括號 {} 和小括號 () 有不同的含義和作用。 大括號 {}&#xff1a; 初始化對象&#xff1a;當在聲明類對象時使用大括號 {} 時&#xff0c;這表示對對象進行初始化。這種方式也稱為列表初始化或者統一初始化。示例&#xff1a;MyClass obj{};…

網上下載的pdf文件,為什么不能復制文字?

不知道大家有沒有到過這種情況&#xff1f;在網上下載的PDF文件打開之后&#xff0c;發現選中文字之后無法復制。甚至其他功能也都無法使用&#xff0c;這是怎么回事&#xff1f;該怎么辦&#xff1f; 當我們發現文件打開之后&#xff0c;編輯功能無法使用&#xff0c;很可能是…

AlexNet

概念 過擬合:根本原因是特征維度過多&#xff0c;模型假設過于復雜&#xff0c;參數過多&#xff0c;訓練數據過少&#xff0c;噪聲過多&#xff0c;導致擬合的函數完美的預測訓練集&#xff0c;但對新數據的測試集預測結果差。 過度的擬合了訓練數據&#xff0c;而沒有考慮到…

29、卷積 - 參數 padding 的作用

在卷積過程中,Padding(填充)是一個關鍵的概念,它對于保留輸入信息和有效地處理邊緣信息至關重要。 1、Padding是什么? Padding 指的是在輸入圖像的周圍添加額外的像素值,用來以擴大輸入圖像的尺寸,這些額外填充的像素值通常設置為零,卷積操作在這個填充后的輸入圖像上…

C#基礎-結構體應用實例

目錄 定義 結構有以下特點 用法實例 定義 在 C# 中,結構體是值類型數據結構。它使得一個單一變量可以存儲各種數據類型的相關數據。struct 關鍵字用于創建結構體。 結構有以下特點 結構可帶有方法、字段、索引、屬性

2024年生成式人工智能發展預測

2024年生成式人工智能發展預測 2023.12.9版權聲明&#xff1a;本文為博主chszs的原創文章&#xff0c;未經博主允許不得轉載。 當前&#xff0c;生成式人工智能&#xff08;Generative AI&#xff0c;后面簡稱 Gen AI&#xff09;領域不但在持續演進&#xff0c;而且它正在徹…