22javascript筆記(2)

小島的每一段verse發表於2021-08-18

JavaScript

1.js事件和作用域

js事件:html頁面中每一個元素都可以產生某些觸發js函式的事件。這些事件是可以被js偵測到的一種行為,並且js程式能應對這些事件。

常見的html事件

onchange:html元素改變

onclick:使用者點選html元素

onmouseover:使用者吧滑鼠移到html元素上

onmouseout:使用者從html元素移開滑鼠

onkeydown:使用者按下鍵盤按鍵

onkeyup:瀏覽器完成頁面的載入

HTML頁面完成載入

HTML輸入欄位被使用者更改

HTML按鈕被使用者點選

 

設定元素的js事件:行內方法

<element event="JavaScript 程式碼"></element>
<element event='JavaScript 程式碼'></element>
<button onclick="getElementById('demo').innerHTML=Date()">

 

innerHTML屬性設定元素的內容

設定元素的事件:內部方法

 <button onclick="displayDate()">點選這裡 p 標籤的內容將被修改</button>
<script>
      function displayDate() {
        document.getElementById("demo").innerHTML = Date();
      }
</script>

 

js作用域

js中有全域性作用域和區域性作用域

區域性作用域:在函式內宣告的變數為區域性變數,作用域只在函式內部有效,也只能被函式內部訪問。 不同函式中可以宣告同名的區域性變數,區域性變數的生命週期是函式的生命週期。

<script>
      myFtn();
    
      function myFtn() {
        var lanqiaoxueyuan = "www.lanqiao.cn";
       document.getElementById("demo1").innerHTML =
          "lanqiaoxueyuan" + " = " + lanqiaoxueyuan;
      }
      document.getElementById("demo2").innerHTML = typeof lanqiaoxueyuan;//undefined
</script>

 

全域性作用域:在函式外宣告的變數。全域性變數作用域針對整個全域性。網頁的所有指令碼和函式都能訪問它。

<script>
      var lanqiaoxueyuan = "www.lanqiao.cn";
      myFtn();
​
      function myFtn() {
        document.getElementById("demo").innerHTML =
          "我能顯示 " + lanqiaoxueyuan;
      }
</script>

 

自動全域性:如果變數在函式內沒有宣告(沒有使用var關鍵字),該變數為全域性變數。

<script>
      myFtn();
​
      // 此處的程式碼可以把 lanqiaoxueyuan 作為全域性變數使用。
      document.getElementById("demo").innerHTML =
        "我可以顯示 " + lanqiaoxueyuan;//沒有宣告直接使用
function myFtn() {
        lanqiaoxueyuan = "www.lanqiao.cn";
      }
</script>

 

js變數生命週期

js變數在宣告時開始初始化,區域性變數在函式銷燬後自動銷燬,全域性變數在頁面關閉後進行銷燬

函式引數:只在函式內部起作用,是區域性變數

全域性變數:window是全域性物件,因此任何全域性變數都屬於window物件,是它的一個屬性。

如果沒有特殊需求,不要建立全域性變數,因為它會覆蓋window變數(或函式),任何函式,包括window物件,能覆蓋全域性變數和函式。

2.js字串和運算子

js字串:單引號或者雙引號引起來的unicode字元序列。用於儲存和操作文字。

str.length

轉移符號

通常,js字串是原始資料,可以使用字元建立。

var lanqiaoxueyuan = "www.lanqiao.cn";

 

但也可以使用new關鍵字將字串定義為一個物件。

var lanqiaoxueyuan = new String("www.lanqiao.cn");

 

雖然String物件可以建立,但是它會拖慢執行速度,並可能產生其他副作用。

因為字串與物件、物件與物件無法比較。

js運算子:算術運算子 + - * / % ++(左、右) --(左、右)

賦值運算子: = += -= *= /= %=

字串+數字、字串+字串

3.js的資料型別轉換

js六種可包含值的資料型別:

  • 字串String

  • 數字Number

  • 布林Boolean

  • 物件Object

  • 函式function

  • 唯一的symbol

三中物件型別:

  • 物件Object

  • 日期Date

  • 陣列Array

兩種值唯一的資料型別:

  • null

  • undefined

使用typeof運算子返回變數、物件、表示式的型別

NaN的資料型別是Number

陣列Array的資料型別是Object

日期Date的資料型別是Object

null的資料型別是Object

undefined的資料型別是undefined

undefined是null的一種,undefined == null為true

 

constructor屬性用於返回js變數的建構函式

<script>
      document.getElementById("demo").innerHTML =
        "JACK".constructor +//String()
        "<br>" +
        (3.14).constructor +//Number()
        "<br>" +
        false.constructor +//Boolean()
        "<br>" +
        [1, 2, 3, 4, 5].constructor +//Array()
        "<br>" +
        { name: "JACK", age: 36 }.constructor +//Object()
        "<br>" +
        new Date().constructor +//Date()
        "<br>" +
        function () {}.constructor;//Function()
    </script>

 

可以通過constructor屬性來確定某個物件是否為陣列或日期(如果用typeof,都是object)

 <script>
      var haha = ["Women", "Meitian", "Douyao", "Kaixin"];
      document.getElementById("demo").innerHTML = isArray(haha);
      function isArray(myArray) {
        return myArray.constructor.toString().indexOf("Array") > -1;
      }
    </script>

 

js型別轉換

js型別轉換有兩種方式:使用js函式、js自身自動轉換

數字轉字串:全域性String()方法、number.toString()

布林值轉字串:全域性String()方法、boolean.toString()

日期轉字串:Date()返回字串、String()

 

字串轉數字:

全域性Number():

字串為數值,可以轉換成數字、空字串轉換為0、其他字串轉換為NaN(非數值型別)

Number("3.14"); // 返回 3.14
Number(" "); // 返回 0
Number(""); // 返回 0
Number("99 88"); // 返回 NaN

 

一元運算子+:

        var a = "6";//String
        var b = +a;//Number
        document.getElementById("demo").innerHTML =
          typeof a + "<br>" + typeof b;

 

使用+可以String轉換為Number,如果轉換不成功會變成NaN

布林值轉數字:false為0 true為1

全域性Number()方法

日期轉數字:轉換為毫秒數

全域性Number()方法,等同於d.getTime()

 

自動型別轉換:

console.log(5 + null);//5 null轉為0
console.log("5" + null);//5null null轉為“null”
console.log("5" + 1);//51 1轉為“1”
console.log("5" - 1);//4 “5”轉為5

 

自動轉為字串:

當嘗試輸出一個物件或變數時,會自動呼叫變數的toString()方法

 

布林值與字串:“” “ ”為false 有值的字串為true

NaN為false +-Infinity為true

“”為數字0

[]為數字0,“”,true

[20]為數字20,"20",true

function(){}為NaN,true

null為數字0,false

undefined為NaN,false

4.js的正規表示式

js的regex語法:/pattern/modifiers

var patt = /lanqiaoxueyuan/i;

 

js的正規表示式經常使用兩個字串方法:

search():返回匹配的位置

replace():返回模式被替換出修改後的字串

test():解析字串,如果符合正規表示式返回true,否則返回false

 var str = "Search lanqiaoxueyuan";
 var a = str.search(/lanqiaoxueyuan/i);//7
 var str = document.getElementById("demo").innerHTML;
        var txt = str.replace(/lanqiaoxueyuan/i, "www.lanqiao.cn");
var a = new RegExp("f");
a.test(
          "Attitude determines life, and should not let life determine your attitude!"
        );
var patt1 = new RegExp("f");
 patt1.exec(
          "Attitude determines life, and should not let life determine your attitude!"
        );

 

regex修飾符:

i 執行對大小寫不敏感的匹配

g 執行全域性匹配

m 執行多行匹配

regex常用模式:

(x|y):以|分割的選項

\d:數字

\w:數字、字母、下劃線

\b:單詞邊界

\uxxxx:Unicode(16進位制)

\s:空白字元

量詞:

n+ 至少一個n

n* 任意n

n? 零個或一個n

5.原型

js中給函式提供了一個物件型別的屬性,叫做Prototype(原型)

原型歸所有函式所有,他不用建立 是預設存在存在的

function Car(){
​
}
var c1 = new Car();
var c2 = new Car();
Car.prototype.name = "BMW";
console.log(c1.name);
console.log(c2.name);

 

js提供了這樣的一種機制,如果是通過建構函式建立物件,當訪問你的屬性在物件中沒有找到,則去建立物件的建構函式中找,如果能找到,也相當於物件擁有這個屬性

原型的作用就是為類(函式)提供了一個公共區域,在這個公共區域宣告的屬性和方法能夠被所有通過這個類建立的物件所訪問到。

function Car(name,speed,ability){
     this.name = name;
     this.speed = speed;
     this.ability = ability;
 }
 Car.prototype.showAbility= function(){
     console.log(this.ability);
 }
 var c1 = new Car("BMW",240,"坐寶馬");
 var c2 = new Car("BZ",300,"開賓士");
 c1.showAbility();
 c2.showAbility();

 

原型是js為所有函式所建立的一個物件型別的屬性,原型當中的屬性和方法被所有的通過這個函式所建立的所有物件共享。

 

結構: 原型是一個物件,在原型中通常擁有兩個屬性

1 構造器: constructor 該屬性指向這個函式本身

2 原型指向

__proto__該屬性指向原型本身,提供給通過類建立的物件使用

作用: 原型用來建立類的共有屬性和共有方法,為建立物件服務

優點: 節約記憶體空間,不必為每一個物件分配共有屬性和共有方法的記憶體

缺點: 原型中不能儲存陣列這類引用型別的資料,因為地址的傳遞的問題 會導致出現修改的連鎖變換。

 

6.原型鏈

建構函式的屬性prototype可以設定共有屬性和共有方法 物件擁有proto和constructor屬性,但是函式也是一種物件,所以函式也有這兩種屬性 proto是由一個物件指向一個物件,即指向他們的原型物件(父物件)。proto 的作用是,當物件找一個屬性沒找到時,就去它的父物件裡找,再往父物件的父物件裡找。最後形成了一條原型鏈。 prototype是函式獨有的,從一個函式指向一個物件,也就是這個函式建立的例項的原型物件,即f1.proto===Foo().prototype。prototype屬性的作用是包含可以讓特定型別的所有例項共享的屬性和方法。 constructor是物件獨有的,從一個物件指向一個函式,含義就是指向該物件的建構函式。每個物件都有建構函式,Function的建構函式就是它自己。所以constructor的重點就是Function這個函式。

  
    console.log(c1.__proto__);//獲取到c1的建構函式的原型
        console.log(c1.__proto__===Car.prototype);//Car.prototype,true
        console.log(c1.__proto__.__proto__);//獲取到物件的原型,所有物件的原型即Object()定義的公共屬性和方法
        console.log(c1.__proto__.__proto__===Object.prototype);//Object.prototype,true
        console.log(c1.__proto__.__proto__.__proto__);//Object.prototype沒有公共屬性
        console.log(c1.__proto__.__proto__.__proto__);
        console.log(new Object().__proto__);//object物件.__proto__===Object()的原型
        console.log(new Object().constructor.prototype);//Object()的原型
        console.log(new Object().__proto__.__proto__);
        console.log(Object.prototype.constructor.prototype);//如果一直對Object物件呼叫構造方法再獲取公共屬性,會一直套娃。