Web前端基礎(12):JavaScript(六)

来源:https://www.cnblogs.com/liuhui0308/archive/2019/11/18/11883934.html
-Advertisement-
Play Games

1. JS中的面向對象 創建對象的幾種常用方法: 1.使用Object或對象字面量創建對象 2.工廠模式創建對象 3.構造函數模式創建對象 4.原型模式創建對象 1.1 使用Object或對象字面量創建對象 JS中最基本創建對象的方式: var student = new Object(); stu ...


1. JS中的面向對象

創建對象的幾種常用方法:

1.使用Object或對象字面量創建對象

2.工廠模式創建對象

3.構造函數模式創建對象

4.原型模式創建對象

1.1 使用Object或對象字面量創建對象

JS中最基本創建對象的方式:

var student = new Object();
student.name = "easy";
student.age = "20";

這樣,一個student對象就創建完畢,擁有2個屬性name以及age,分別賦值為"easy"20

如果你嫌這種方法有一種封裝性不良的感覺。來一個對象字面量方式創建對象。

var sutdent = {
  name : "easy",
  age : 20
};

這樣看起來似乎就完美了。但是馬上我們就會發現一個十分尖銳的問題:當我們要創建同類的student1,student2,…,studentn時,我們不得不將以上的代碼重覆n次。

var sutdent1 = {
  name : "easy1",
  age : 20
};

var sutdent2 = {
  name : "easy2",
  age : 20
};

...

var sutdentn = {
  name : "easyn",
  age : 20
};

有個提問?能不能像工廠車間那樣,有一個車床就不斷生產出對象呢?我們看”工廠模式”。

1.2 工廠模式創建對象

JS中沒有類的概念,那麼我們不妨就使用一種函數將以上對象創建過程封裝起來以便於重覆調用,同時可以給出特定介面來初始化對象。

function createStudent(name, age) {
  var obj = new Object();
  obj.name = name;
  obj.age = age;
  return obj;
}

var student1 = createStudent("easy1", 20);
var student2 = createStudent("easy2", 20);
...
var studentn = createStudent("easyn", 20);

這樣一來我們就可以通過createStudent函數源源不斷地”生產”對象了。看起來已經高枕無憂了,但貪婪的人類總有不滿足於現狀的天性:我們不僅希望”產品”的生產可以像工廠車間一般源源不斷,我們還想知道生產的產品究竟是哪一種類型的。

比如說,我們同時又定義了”生產”水果對象的createFruit()函數:

function createFruit(name, color) {
  var obj = new Object();
  obj.name = name;
  obj.color = color;
  return obj;
}

var v1 = createStudent("easy1", 20);
var v2 = createFruit("apple", "green");

對於以上代碼創建的對象v1、v2,我們用instanceof操作符去檢測,他們統統都是Object類型。我們的當然不滿足於此,我們希望v1是Student類型的,而v2是Fruit類型的。為了實現這個目標,我們可以用自定義構造函數的方法來創建對象。

1.3 構造函數模式創建對象

在上面創建Object這樣的原生對象的時候,我們就使用過其構造函數:

var obj = new Object();

在創建原生數組Array類型對象時也使用過其構造函數:

var arr = new Array(10);  //構造一個初始長度為10的數組對象

在進行自定義構造函數創建對象之前,我們首先瞭解一下構造函數普通函數有什麼區別。

1、實際上並不存在創建構造函數的特殊語法,其與普通函數唯一的區別在於調用方法。對於任意函數,使用new操作符調用,那麼它就是構造函數;不使用new操作符調用,那麼它就是普通函數。

2、按照慣例,我們約定構造函數名以大寫字母開頭,普通函數以小寫字母開頭,這樣有利於顯性區分二者。例如上面的new Array(),new Object()。

3、使用new操作符調用構造函數時,會經歷(1)創建一個新對象;(2)將構造函數作用域賦給新對象(使this指向該新對象);(3)執行構造函數代碼;(4)返回新對象;4個階段。

瞭解了構造函數普通函數的區別之後,我們使用構造函數將工廠模式的函數重寫,並添加一個方法屬性: 

function Student(name, age) {
  this.name = name;
  this.age = age;
  this.alertName = function(){
    alert(this.name)
  };
}

function Fruit(name, color) {
  this.name = name;
  this.color = color;
  this.alertName = function(){
    alert(this.name)
  };
}

這樣我們再分別創建Student和Fruit的對象:

var v1 = new Student("easy", 20);
var v2 = new Fruit("apple", "green");

這時我們再來用instanceof操作符來檢測以上對象類型就可以區分出Student以及Fruit了:

alert(v1 instanceof Student);  //true
alert(v2 instanceof Student);  //false
alert(v1 instanceof Fruit);  //false
alert(v2 instanceof Fruit);  //true

alert(v1 instanceof Object);  //true 任何對象均繼承自Object
alert(v2 instanceof Object);  //true 任何對象均繼承自Object

這樣我們就解決了工廠模式無法區分對象類型的尷尬。那麼使用構造方法來創建對象是否已經完美了呢?使用構造器函數通常在js中我們來創建對象。

我們會發現Student和Fruit對象中共有同樣的方法,當我們進行調用的時候這無疑是記憶體的消耗。

我們完全可以在執行該函數的時候再這樣做,辦法是將對象方法移到構造函數外部:

function Student(name, age) {
  this.name = name;
  this.age = age;
  this.alertName = alertName;
}

function alertName() {
  alert(this.name);
}

var stu1 = new Student("easy1", 20);
var stu2 = new Student("easy2", 20);

在調用stu1.alertName()時,this對象才被綁定到stu1上。

我們通過將alertName()函數定義為全局函數,這樣對象中的alertName屬性則被設置為指向該全局函數的指針。由此stu1和stu2共用了該全局函數,解決了記憶體浪費的問題

但是,通過全局函數的方式解決對象內部共用的問題,終究不像一個好的解決方法。如果這樣定義的全局函數多了,我們想要將自定義對象封裝的初衷便幾乎無法實現了。更好的方案是通過原型對象模式來解決。

1.4 原型的模式創建對象

原型鏈甚至原型繼承,是整個JS中最難的一部分也是最不好理解的一部分,在這裡由於我們課程定位的原因,如果對js有興趣的同學,可以去查閱一下相關JS原型的一些知識點。更加有助於你以後前端JS的面試。

function Student() {
    this.name = 'easy';
    this.age = 20;
}

Student.prototype.alertName = function(){
    alert(this.name);
};

var stu1 = new Student();
var stu2 = new Student();

stu1.alertName();  //easy
stu2.alertName();  //easy

alert(stu1.alertName == stu2.alertName);  //true 二者共用同一函數

2. 定時器

在js中的定時器分兩種:1、setTimeout() 2、setInterval()。

2.1 setTimeOut()

只在指定時間後執行一次

/定時器 非同步運行  
function hello(){  
alert("hello");  
}  
//使用方法名字執行方法  
var t1 = window.setTimeout(hello,1000);  
var t2 = window.setTimeout("hello()",3000);//使用字元串執行方法  
window.clearTimeout(t1);//去掉定時器

2.2 setInterval()

在指定時間為周期迴圈執行

/實時刷新  時間單位為毫秒  
setInterval('refreshQuery()',8000);   
/* 刷新查詢 */  
function refreshQuery(){  
  console.log('每8秒調一次') 
}

兩種方法根據不同的場景和業務需求擇而取之。

對於這兩個方法,需要註意的是如果要求在每隔一個固定的時間間隔後就精確地執行某動作,那麼最好使用setInterval,而如果不想由於連續調用產生互相干擾的問題,尤其是每次函數的調用需要繁重的計算以及很長的處理時間,那麼最好使用setTimeout。


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 網站的favicon圖標 favicon.ico一般用於作為縮略的網站標誌,它顯示在瀏覽器的地址欄或者標簽上。 製作favicon圖標 把圖片轉換為png圖片 把png圖片轉換為ico圖標,這需要藉助第三方轉換網站,例如比特蟲:http://www.bitbug.net/ favicon圖標放到網站 ...
  • 1. jQuery選擇器 jQuery選擇器是jQuery強大的體現,它提供了一組方法,讓我們更加方便的獲取到頁面中的元素。 1.1 基本選擇器 例子如下: <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>< ...
  • CSS3的新特性 1. 新增CSS3特性有相容性問題,ie9+才支持 2. 移動端支持優於PC端 3. 新增選擇器和盒子模型以及其他特性 4. CSS新增選擇器 屬性選擇器 屬性選擇器可以根據元素特定屬性來選擇元素,這樣就可以不用藉助於類或者id選擇器 | 選擇符 | 簡介 | | | | | E[ ...
  • 1. jQuery概述 1.1 為什麼要使用jQuery 在用js寫代碼時,會遇到一些問題: window.onload 事件有事件覆蓋的問題,因此只能寫一個事件。 代碼容錯性差。 瀏覽器相容性問題。 書寫很繁瑣,代碼量多。 代碼很亂,各個頁面到處都是。 動畫效果很難實現。 jQuery的出現,可以 ...
  • 示例代碼托管在: "http://www.github.com/dashnowords/blogs" 博客園地址: "《大史住在大前端》原創博文目錄" 華為雲社區地址: "【你要的前端打怪升級指南】" [TOC] 一. 硬體加速相關的幾個概念 之前介紹到了 渲染層的概念,在涉及到硬體加速的話題時,出 ...
  • 需求:使用多張圖片作為頁面的背景圖; 首先需要瞭解background的屬性以及細節知識:https://www.cnblogs.com/chenglj/p/7372996.html background-image:url("1.jpg"),url("2.jpg"),url("3.jpg"); b ...
  • 一、html概念 1、定義:(Hyper Text Markup Language)超文本標記語言,主要是通過html標記對網頁中的文本,圖片,聲音等內容進行描述,同時也可以在文本中包含“超級鏈接”,通過超鏈接實現網頁跳轉。 2、編碼格式: gb2312:國家標準第2312條定義了簡體字元,部分亞裔 ...
  • 1. BOM JavaScript基礎分為三部分: ECMAScript:JavaScript的語法標準。包括變數、表達式、運算符、函數、if語句、for語句等。 DOM:文檔對象模型,操作網頁上的元素的API。比如讓盒子移動、變色、輪播圖等。 BOM:瀏覽器對象模型,操作瀏覽器部分功能的API。比 ...
一周排行
    -Advertisement-
    Play Games
  • 示例項目結構 在 Visual Studio 中創建一個 WinForms 應用程式後,項目結構如下所示: MyWinFormsApp/ │ ├───Properties/ │ └───Settings.settings │ ├───bin/ │ ├───Debug/ │ └───Release/ ...
  • [STAThread] 特性用於需要與 COM 組件交互的應用程式,尤其是依賴單線程模型(如 Windows Forms 應用程式)的組件。在 STA 模式下,線程擁有自己的消息迴圈,這對於處理用戶界面和某些 COM 組件是必要的。 [STAThread] static void Main(stri ...
  • 在WinForm中使用全局異常捕獲處理 在WinForm應用程式中,全局異常捕獲是確保程式穩定性的關鍵。通過在Program類的Main方法中設置全局異常處理,可以有效地捕獲並處理未預見的異常,從而避免程式崩潰。 註冊全局異常事件 [STAThread] static void Main() { / ...
  • 前言 給大家推薦一款開源的 Winform 控制項庫,可以幫助我們開發更加美觀、漂亮的 WinForm 界面。 項目介紹 SunnyUI.NET 是一個基於 .NET Framework 4.0+、.NET 6、.NET 7 和 .NET 8 的 WinForm 開源控制項庫,同時也提供了工具類庫、擴展 ...
  • 說明 該文章是屬於OverallAuth2.0系列文章,每周更新一篇該系列文章(從0到1完成系統開發)。 該系統文章,我會儘量說的非常詳細,做到不管新手、老手都能看懂。 說明:OverallAuth2.0 是一個簡單、易懂、功能強大的許可權+可視化流程管理系統。 有興趣的朋友,請關註我吧(*^▽^*) ...
  • 一、下載安裝 1.下載git 必須先下載並安裝git,再TortoiseGit下載安裝 git安裝參考教程:https://blog.csdn.net/mukes/article/details/115693833 2.TortoiseGit下載與安裝 TortoiseGit,Git客戶端,32/6 ...
  • 前言 在項目開發過程中,理解數據結構和演算法如同掌握蓋房子的秘訣。演算法不僅能幫助我們編寫高效、優質的代碼,還能解決項目中遇到的各種難題。 給大家推薦一個支持C#的開源免費、新手友好的數據結構與演算法入門教程:Hello演算法。 項目介紹 《Hello Algo》是一本開源免費、新手友好的數據結構與演算法入門 ...
  • 1.生成單個Proto.bat內容 @rem Copyright 2016, Google Inc. @rem All rights reserved. @rem @rem Redistribution and use in source and binary forms, with or with ...
  • 一:背景 1. 講故事 前段時間有位朋友找到我,說他的窗體程式在客戶這邊出現了卡死,讓我幫忙看下怎麼回事?dump也生成了,既然有dump了那就上 windbg 分析吧。 二:WinDbg 分析 1. 為什麼會卡死 窗體程式的卡死,入口門檻很低,後續往下分析就不一定了,不管怎麼說先用 !clrsta ...
  • 前言 人工智慧時代,人臉識別技術已成為安全驗證、身份識別和用戶交互的關鍵工具。 給大家推薦一款.NET 開源提供了強大的人臉識別 API,工具不僅易於集成,還具備高效處理能力。 本文將介紹一款如何利用這些API,為我們的項目添加智能識別的亮點。 項目介紹 GitHub 上擁有 1.2k 星標的 C# ...