/Users/yangyangzi/Desktop/YangZi2/JavaScript/JavaScript.rtfd (公司電腦)
7.8
編譯型語言:程序執行之前,需要專門的一個編譯過程,把程序編譯成爲機器語言的文件,比如exe文件;強類型語言,java c++
解釋型語言:程序執行之前,不需要編譯,直接運行時邊解析邊執行的語言弱類型語言 python php ;
JavaScript的組成:
ECMAScript:ECMA即歐洲計算機製造商協會;ECMAScript是ECMA指定的腳本語言的標準,規定了一種腳本語言實現應該包含的基本內容
DOM:JavaScript操作網頁上元素的API
BOM:JavaScript操作瀏覽器的部分功能的API
DOM樹:Document Object Model,即文檔對象模型
DOM可以以一種獨立於平臺和語言的方式訪問和修改一個文檔的內容和結構。換句話說,這是表示和處理一個HTML或XML文檔的常用方法。有一點很重要,DOM的設計是以對象管理組織(OMG)的規約爲基礎的,因此可以用於任何編程語言。最初人們把它認爲是一種讓JavaScript在瀏覽器間可移植的方法,不過DOM的應用已經遠遠超出這個範圍。Dom技術使得用戶頁面可以動態地變化,如可以動態地顯示或隱藏一個元素,改變它們的屬性,增加一個元素等,Dom技術使得頁面的交互性大大地增強,通過 JavaScript,您可以重構整個 HTML 文檔。您可以添加、移除、改變或重排頁面上的項目。
https://baike.baidu.com/item/DOM/50288?fr=aladdin
BOM:Browser Object Model,即瀏覽器對象模型。瀏覽器在頁面初始化時,會在內存創建一個全局對象,用來描述當前窗口的屬性和狀態,這個全局對象被稱爲瀏覽器對象模型
不同於DOM的標準化組織是W3C,JavaScript的語法標準是ECMA,BOM沒有官方標準,對於現代瀏覽器,每個瀏覽器都有自己的BOM實現方法,所有直接使用BOM會有兼容性問題,但是爲了利用JavaScript完成交互,現代瀏覽器幾乎都實現了相同的方法和屬性,這些方法和屬性被稱作BOM方法和屬性
BOM包含:有個核心對象window,window包含6大核心模塊,分別是:document對象,渲染引擎在解析HTML對象時,會生成一個document對象,即文檔對象,它是HTML文檔的根節點。每一個元素都會生成對應的DOM對象,由於元素之間有層級關係,整個HTML代碼解析結束後,會生成一個由不同節點組成的樹形結構,成爲DOM樹。用於描述DOM樹的狀態和屬性,並提供了很多操作DOM的API
frames,即HTML自框架
History,頁面歷史記錄;window.history對象包含瀏覽器的歷史記錄,window可以省略。這些歷史記錄以棧(FIFO)的形式保存。頁面前進則入棧,頁面返回則出棧
location,當前頁面地址
navigator,瀏覽器相關信息
screen,用戶顯示屏幕相關屬性
DOM
Js的所有全局對象、全局方法、全局變量全部自動被歸爲iwindow對象的方法和屬性,在調用這些方法和屬性時可以省略window。DOM是window對象的屬性
BOM https://www.jianshu.com/p/0c8b34111e95
1、js的樣式(類似於css的三種樣式,只不過js用<javascript標籤>而css用<style標籤>):
行內樣式:
頁面演示:
外鏈樣式:
注意:引入路徑
Html用的是相對路徑:
前端使用的相對路徑 /; ./; ../../; ../../../;https://blog.csdn.net/cvper/article/details/79955412
前端入門—相對路徑和絕對路徑https://blog.csdn.net/qianduanshuo/article/details/90612917
7.11
常用輸出方式
1、彈框輸出;alert(“alert彈框”)
2、控制檯輸出;運行時F12,出現控制檯打印;
console.log(“sd”) console.error(“錯誤輸出”) console.warn(“警告輸出”)
3、用戶輸入:prompt(“請輸入用戶名”)
4、確定取消彈框:confirm(“彈框”) 確定;取消
註釋:單行多行註釋同oc
單行註釋可以包含多行註釋
多行註釋能包含單行註釋
多行註釋不能包含多行註釋
常量,變量,標識符
變量:var
關鍵字,保留字
標識符:可以自主命名的,可以有字母、數字、下劃線$,不能以數字開頭,不能是關鍵字;嚴格區分大小寫;駝峯式寫法,utf8支持的都可以
數據和數據類型
6種:
一、簡單數據類型(棧):
1、數字類型:number 不區分浮點型和整型
最大值;最小值;無窮大Infinity;無窮小 -Infinity
;NaN:NaN:not a number ,js中對數值進行計算時,如果沒有結果,則返回NaN;整數可以保證精準值,小數時會丟失精度
(解決js的精度丟失問題:放大倍數,運算完再縮小回去https://blog.csdn.net/tinsine/article/details/77841031)
2、字符串類型:string
相同引號不能嵌套,不同引號可以嵌套:單引號內可以放雙引號,不能放單引號;雙引號內可以放單引號,但不能放雙引號
3、布爾類型:boolean (邏輯類型 或 真假類型)
//任何非0都爲true
//任何非空字符串都是true
//任何對象都是true
4、變量未初始化:undefined
Undefined是一種特殊類型,表示變量未賦值,這種變量有一種值就是undefined;只有一個值的數據類型
小寫的undefined和10,abc等一樣是一個常量;大寫的Undefined和Number,Boolean一樣是一種數據類型;
typeof()函數對沒有初始化或沒有賦值的變量都會返回undefined
5、空類型:Null
Null類型和Undefined一樣只有一個特殊值的數據類型,這個特殊值就是null
Null是一個空的對象,所有使用typeof檢查null會返回一個Object類型
undefined值是由null值衍生出來的,所以如果比較undefined和null是否相等會返回true
== 值比較 ===值比較+類型比較
var aa = undefined
var bb = null
console.log(aa == bb) //true
console.log(aa === bb)//false
二、複雜數據類型(堆):
1、對象類型:Object
2、數組類型:Array
查看類型 type of()
7.12
數據類型轉化
一、其他類型轉換成string
1、toString()
toString()函數不能用於undefined和null,但是可以用於NaN類型
2、String()
// 有些類型並沒有toString()方法,這時候可以用String()函數;例如undefined和null
var num
console.log(String(num))
var num1 = null
console.log(String(num1))
var num2 = undefined
console.log(String(num2))
3、強轉用+
任何數據和+都會轉換成string類型
二、其他類型轉換成Number
1、Number()函數
1》、純數字的字符串,則直接轉換爲數字
2》、包含非數字內容的字符串,會返回NaN
3》、空或一堆空格,返回0
4》、undefined,返回NaN
5》、null,返回0
6》、Boolean,true返回1,false返回0
2、parseInt()函數 parseFloat()函數的
從左向右轉化,遇到非數字則停止轉換
var str3 = '123.33rr4.67'
console.log(parseInt(str3),typeof parseInt(str3),parseFloat(str3),typeof parseFloat(str3))
結果:123 "number" 123.33 "number"
Js的運算符:
Number類型打印結果是藍色
字符串類型打印結果是黑色
一、算數運算符:
1、加法運算符:num1 + num2
1》非Number類型的值進行運算時,會先將這些值轉化爲Number類型然後在做運算;
2》任何值和NaN運算時,都得NaN;
3》任何值和字符串運算,都會先轉換成字符串,再進行字符串的拼接操作
2、減法運算符:num1 - num2
1》非Number類型的值進行運算時,會先將這些值轉化爲Number類型然後在做運算;
2》任何值和NaN運算時,都得NaN;
3》字符串做減法會轉換成Number :var num = 123 - '3' console.log(num);結果打印120;這點與加法運算符不同
3、乘法運算符:num1 * num2
注意點和減法一樣(如下)
1》非Number類型的值進行運算時,會先將這些值轉化爲Number類型然後在做運算;
2》 任何值和NaN運算時,都得NaN;
3》字符串做乘法會轉換成Number
4、除法運算符:num1 / num2
注意點和減法一樣(如下)
1》非Number類型的值進行運算時,會先將這些值轉化爲Number類型然後在做運算;
2》任何值和NaN運算時,都得NaN;
3》字符串做除法會轉換成Number
5、取餘運算符:num1 % num2
m % n 相當於 m / n獲取餘數
n爲0 返回NaN 注意此處和除法不同,取餘分母爲0結果爲NaN,而除法分母爲0結果爲Infinity
m爲0 返回0
m>n 正常求餘
m<n 返回m
其他規律和減法一樣:
非Number先轉化Number,再運算
任何值和NaN運算,都是NaN
字符串取餘會轉化成Number
二、正負運算符:
正號:+對數字無影響
var var2 = - 12
var var22 = +var2//還是-12
對非Number類型的值會轉換爲Number,然後運算
var var3 = + '13'//字符串 13
var var4 = + true//布爾 +1
var var6 = +null//null +0
負號:-對數字進行負號取反
三、賦值運算符:
簡單賦值運算符:=
複雜賦值運算符:*= ;/=;+=
四、自增運算符:++ —
i = i+1 i = i-1
// a++ 先運算,再++
var num1 = 20, num2 = 30
var num3 = (num1 ++) + (num2 ++)
console.log(num3,num1,num2);//50,21,31
// --a 先--,再運算
var a1 = 20,a2 = 30
var a3 = (--a1) + (--a2)
console.log(a3,a1,a2);//48,19,29
五、關係運算符:返回值爲true或false
>
<
>=
<=
== 值等於
!= 值不等於
=== 值和類型等於
!== 值和類型不等於
注意:
對於非數值進行比較時,會將其轉換爲數字然後再比較
如果符號兩側都是字符時,則會比較兩側字符串中字符的Unicode編碼
null、undefined、NaN比較
//如果左側是數值,則右側會先轉換成數值再進行比較
console.log(a > false)//true
//如果左側爲字符則比較比較字符串中字符的unicode編碼
console.log( "a" > "b")//false a、b的unicode編碼分別爲97、98
console.log(null == 0)//false
console.log(undefined == 0)//false
console.log(NaN == 0)//false
console.log(0 == null)//false Number(null)爲0,所以這裏感覺很奇怪
console.log(0 == undefined)//false
console.log(0 == NaN)//false
console.log(Number(null),Number(undefined),Number(NaN))// 0 NaN NaN
console.log(null == null)//true
console.log(undefined == undefined)//true
console.log(NaN == NaN)//false
console.log(null == undefined)//true
console.log(undefined == null)//true
console.log(null === undefined)//false
// isNaN()函數,專門判斷是否是數字,如果參數是數字則返回false,參數爲非數字則返回true
console.log(isNaN(mm));//false
console.log(isNaN(null));//false * ;可能是Number(null)結果爲0,相當於判0
console.log(isNaN(undefined));//true ; 可能是Number(undefined)結果爲NaN,相當於判NaN
console.log(isNaN(NaN))//true d
六、邏輯運算符:
&&(與)
&&的短路寫法:條件 && 某種結果
console.log(Boolean(alert("d")))//false
console.log(alert('dd'))//undefined
var a = 123 && alert('短路寫法')
console.log(a)//沒有返回true,返回結果是undefined(並沒有將alert('短路寫法')自動轉換爲boolean後再計算)
a = true && alert('短路寫法1')
console.log(a)//沒有返回true,返回結果是undefined
a = false && alert('短路寫法2')
console.log(a)//false
&&注意點:
1、如果&&兩側是非boolean,邏輯與會將其自動轉換爲boolean類型來判斷(這句話對於短路寫法有問題,上邊返回undefined的示例則推翻此結論,故不要盲從)
var b = 123 && 'abc'
console.log(b);//abc
2、如果條件A不成立,則返回A
b = false && 'abc'//false
console.log(b);
3、如果條件A成立,則不管B成不成立都返回B
b = true && 'abc'//abc
console.log(b);
|| (或)
||注意點:
1、如果A不成立,則不管B是否成立則返回B數值本身
2、如果A成立,則返回A數值本身
!(非)
對一個值進行兩次取反,其值不變
對非boolean值進行取反,則會將其轉變爲boolean值,然後取反,所有,要想將其它類型轉換爲Boolean類型除了Boolean()函數,還可以使用!!數值;
!!數值的形式實現原理和Boolean()函數一樣
七、逗號運算符
在js中,逗號也是一種運算符,稱爲逗號運算符。其功能是將多個表達式連起來組成一個表達式,稱爲逗號表達式。
表達式1,表達式2,表達式3,…,…,表達式n;逗號表達式的運算過程是:表達式1,表達式2,表達式3,… 表達式n
整個逗號表達式的運算值是最後一個表達式的值
逗號表達式用的比較少
使用注意:
1、程序中使用逗號表達式,通常是要分別求逗號表達式內各個表達式的值,並不一定是求整個逗號表達式的值;
2、並不是所有出現逗號的地方都是逗號表達式,例如多個變量在同一行的聲明並不是逗號表達式
八、三目運算符
如果三目運算符?前的表達式不是boolean值,則會自動轉化爲boolean值
7.15
流程控制語句
注意點:
1、如果只有一條語句,後邊的大括號可以省略
2、分號”;“也是一條語句,空語句
3、if else是一個整體,else先匹配最近的if
4、if小括號內的的語句,先轉換成boolean類型的值,在進行判斷
5、判斷語句的常量與變量問題
6、if語句可以嵌套使用
7.16
If練習
仨數排序
選擇排序:找最小的去對比
//選擇排序
var a = +prompt('第一個數')
var b = +prompt('第二個數')
var c = +prompt('第三個數')
var temp;
if (a > b){
temp = b;
b = a;
a = temp;
}
if (a > c){
temp = c;
c = a;
a = temp;
}
//a此時最小,找最小的
if (b > c){//c最大
temp = c
c = b
b = temp
}
console.log(a,b,c)//從小到大
冒泡排序:找最大的去對比
var res;
var m = +prompt('一')
var n = +prompt('二')
var p = +prompt('三')
if (m > n){
temp = m
m = n
n = temp
}
if (n > p){
temp = n
n = p
p = temp
}
//p是最大的,找最大的
if (m > n){
temp = m
m = n
n = temp
}
console.log(m,n,p)
switch:
使用注意事項:
1、case語句,判斷的是===而非==;也就是說判斷的是類型和數值,而不單單只是數值
2、case後可以是常量也可以是變量
3、表達式的判斷問題:會先計算表達式,在做判斷
4、case穿透:一般是忘記寫break了;或者利用case穿透簡寫,例如輸入月份判斷季節
5、default:default可以省略;且位置可以隨便放
流程控制-循環
while(){}
While循環注意點:
1、死循環,while條件語句永遠是真時
2、任何值都有真假,while條件句執行結果如果不是boolean型,則會先轉換爲bollean再進行判斷
3、while後大括號內只有一條語句時,則大括號可以省略
4、分號問題,類似於if的分號;分號代表一條空語句
5、最簡單的死循環while(1);
Break治癒switch語句或循環語句(跳出當前循環)
Js基礎-數組和函數
構造函數:
字面量;
數組常用函數
//1、join將數組轉換成一個字符串,默認用逗號分割,傳如的參數即分隔符
//2、向數組末尾添加元素,可以填多個(... items),並返回數組個數:push() ;
// 向數組末尾刪除一個元素,並返回此刪除的元素:pop()
//3 刪除數組第一項,並返回第一項,如果數組爲空,則返回undefined:shift()
// 將元素(可以是多個)添加到數組開頭,並返回數組長度
//4 數組翻轉,會影響到原數組:reverse()
//5 concat()將原數組copy一份,並將此函數的參數添加到copy後的數組末尾,如果此函數無參數,則只是copy一份數組
//注意concat與push區別;前者如果添加數組,則會展開數組再添加逐個元素;後者則是添加整個元素
//6、從前開始往後找:indexof(a,b);//a是元素,b是開始從哪個下標查起
// 從後開始往前查找:lastIndexOf(a,b);//a是元素,b是開始從哪個下標查起
//找不到的元素返回-1
7.17
Js的函數:
//函數的聲明
//1、函數的一般聲明
function test() {
console.log(1+3);
}
test()
//2、函數表達式聲明方式(無函數名)
var add = function () {
console.log(1+4);
}
add()
//3、函數 使用Function構造函數
var addadd = new Function('console.log(4+6)')//加單引號的好像有問題
addadd()
var addaddaddadd = new Function(console.log(9+6))
addaddaddadd()
Js的形參和實參(別的語言:一般情況必須實參和形參個數相同,否則會報錯)
Js的形參和實參個數可以不一致
如果實參個數比形參多,則按順序取;同理實參比形參少也是按順序取
<!--arguments對象-->
//包含了傳入函數中的所有參數,arguments並不是一個數組,只是與數組相似,除了length屬性,數組的其他屬性都不具備
//length 函數形參的個數
//函數的length此函數形參個數爲0,實參不爲零(js函數形參和實參個數可以不一樣)
//arguments對象的length爲形參個數
兩個length屬性:
// 注意函數的length屬性和arguments對象的length屬性的區別
// 前者是函數形參的個數,後者是實參的個數
function testArguments(num1,num2) {
console.log('hh',testArguments.length,arguments.length)
if (testArguments.length === arguments.length){
console.log('kk',testArguments.length,arguments.length)
}
}
testArguments(1,3,5)
return:
函數的return使用注意點:
1、如果函數無返回值,默認返回undefined
2、如果函數只有return,return後無值,則返回undefined
3、 如果函數只有return,且return後有值,則返回此值
函數的聲明方式中:
函數一般聲明方式(即函數直接聲明方式)和表達式函數聲明方式的區別:
Js解析器首先會把當前作用域的函數聲明提前到整個作用域的最前面,所以,即使是在函數誰聲明前面調用這個函數也是可以的,但是表達式式函數聲明不具備這種特點,因爲用一個變量接收了此函數
匿名函數:沒有命名的函數
作用:在綁定事件的時候,例如doucument.click = function(){}
定時器 例如setInterval(function(){})
自調用函數:即一進頁面自發執行的操作:(function()(alert(‘hello’)))()
回調函數:
函數調函數
function fn(num1,num2,fun1) {
return fun1(num1,num2);
}
console.log(fn(2, 3, add))//add是函數;add()是函數調用
console.log(fn(2, 3, minus));
console.log(fn(4, 2, divide));
console.log(fn(2, 3, mutiply));
變量的作用域:
全局變量:定義在script或者不屬於某個函數的變量
局部變量:定義在函數內的變量
注意:1、函數內部可以訪問到該函數所屬的外部作用域的變量(作用域鏈),反之不行
2、不使用var聲明的變量是全局變量,即使是在函數內部不使用var聲明的變量也是全局變量
3、局部變量退出作用域之後會銷燬,全局變量關閉網頁或瀏覽器纔會銷燬
作用域鏈:如下,在最小作用域打印a值,a爲3,如果註釋掉3處,則a爲2,註釋掉3處和2處,a爲1,即找a變量的時候,從小範圍到大範圍去尋找,這就是作用域鏈條
{
var a = 1//1
{
var a = 2//2
{
var a = 3//3
console.log(a);
}
}
}
作用域注意:
//1、注意函數內聲明的帶var的變量纔是局部變量
var num = 4;
if (num > 2){
var sum = 4
}
console.log(sum);//注意sum爲全局變量(沒在函數內)
//2、for循環的i變量,在for循環結束依舊能取到
for (var i =0 ;i < 3;i++){
console.log(i)
}
console.log('出來後:',i);//i依舊可以取到
作用域進階:深刻理解js的作用域
<!--作用域進階,很精闢的面試題,深刻理解js的作用域及作用域鏈-->
//1、
var num = 10
fun();
function fun()
console.log(num);
var num = 20;
}
// fun();即使在此調用fun函數,結果也是undefined
//執行結果undefined
/*
* fun函數中,console.log(num);會優先從當前{}中找num變量;
* 找到其下行的var num = 20;
* 但是在此{}中,只是提前了num局部變量的聲明,即fun函數相當於
* function fun() {
* var num;
console.log(num);
num = 20;
}
* 故運行結果爲undefined
* 與fun函數的調用位置無關
* */
//2、
var a = 18;
f1();
function f1() {
var b = 9;
console.log(a);
console.log(b);
var a = '123'
}
/*
* 結果:undefined 9
* 原因同上邊的1
* 即f1函數的聲明相當於
* function f1() {
var b = 9;
var a;
console.log(a);//調用的是當前作用域的a
console.log(b);//調用的是當前作用域的b
a = '123'
}
與f1函數的調用位置無關
* */
console.log('來來來\n')
//3、
f2();
console.log(p);//9
console.log(n);//9
console.log(m);//報錯 m is not defined
function f2() {
var m = n = p = 9;
console.log(m);//9
console.log(n);//9
console.log(p);//9
}
/**
* 注意:同時聲明並初始化多個變量的時候要注意:作用域的區別
*
*f2的函數聲明相當於
* function f2() {
var m = 9;//局部變量
n = 9;//全局變量
p = 9;//全局變量
console.log(m);//9
console.log(n);//9
console.log(p);//9
}
* 故在f2函數外不能調用m
* */
Js作用域與swift作用域對比:
override func viewDidLoad() {
super.viewDidLoad()
view.backgroundColor = UIColor.green
// Do any additional setup after loading the view, typically from a nib.
var name = "麗麗"
func testZYY(){
print(name);
var name:String = "小芳";
}
testZYY()
}
相同的情況,swift不存在js這種奇葩作用域解析方式
作用域進階總結:
Js的函數的聲明和變量的聲明都會被提前到當前作用域的最前面;
而變量的聲明和初始化如果在變量的調用的後邊,則提前到此作用域最前面的只有變量的聲明,而變量的初始化的位置不變(出現undefined現象);
Js基礎-對象和麪向對象:
面向對象:可以創建自定義類型、很好的支持繼承、多態 c++ java c#
基於對象:無法創建自定義類型、不能很好的支持繼承和多態 javascript,但有方法解決上述問題
Js的常見對象:
1、無序屬性的集合:
1》其屬性可以包含基本值、對象或函數
2》對象就是一組沒有順序的值
3》js的對象想象成鍵值對,值可以是數據和函數
2、對象的行爲和特徵:特徵 。。。屬性;行爲。。。方法
3、字面量對象
var dog = {
//屬性
name:'旺財',
age:12,
dogFriends:['花花','小黃','小黑'],
//方法
eat:function () {
console.log('吃')
},
run:function () {
console.log('跑')
}
}
對象的遍歷
for (var i = 0 ; i < dog.left; i++){//無打印
console.log(dog[i])
}
// js對象的遍歷不能用上邊這種for循環,可以用for in
for (var key in dog){
console.log(key,dog[key])
}
構造函數:能產生對象的函數
this的使用:
1、this在哪個對象中,this就代表這個對象
2、誰調用,this就是誰
function test() {
console.log(this)//這裏的this是window,實際是用window調用test()
}
test()
person.sleep();//sleep()函數中的this是person
3、構造函數中的this,始終是new的當前對象
構造函數:
1、通過object的構造函數
function Person() {
var obj = Object()
//屬性
obj.name = null;
obj.age = null;
obj.weight = null;
console.log('dd',this,'sd');
//方法
obj.study = function () {
console.log(this.name,'在學習');
}
obj.sleep = function () {
console.log(this.name,'在睡覺')
}
return obj;
}
var person = Person();
person.name = '劉偉';
person.age = 12;
person.study();
person.sleep()
console.log(person);
2、直接用this的構造函數
function Dog(name,age,friends) {
//屬性
this.name = name;
this.age = age;
this.friends = friends;
//方法
this.eat = function (someThing) {
console.log(this.name,'吃',someThing)
}
this.run = function (someWhere) {
console.log(this.name,'跑到',someWhere)
}
}
var do1 = new Dog('白白',12)
do1.eat('肉肉')
do1.run('home')
var bigDog = new Dog('大黃',14,[do1,'麗麗','花蛤']);
bigDog.eat('骨頭');
bigDog.run('森林');
console.log(bigDog);
console.log(do1 === bigDog)
字面量對象構造函數
//構造函數 將構造函數的參數,轉換爲字面量對象,在用構造函數創建對象時,直接傳整體(字面量對象)//也可以用延展操作符 ...
function Dog(option) {
//屬性
this.name = option.name;
this.age = option.age;
this.friends = option.friends;
}
var do1 = new Dog({name:'白白',age:12})
do1.eat('肉肉')
do1.run('home’)
var bigDog = new Dog({name:'大黃',age:14,friends:[do1,'麗麗','花蛤']});
bigDog.eat('骨頭');
js可以動態的添加屬性或方法
//1、字面量創建方式
var array = [];
var obj = {};//字面量創建對象
//2、構造函數創建方法
var array1 = new Array()
var obj1 = new Object();
// 3、
// constructor屬性 對象的構造方法都有此屬性,通過此屬性可獲得構造函數
// prototype屬性 對象的構造方法都有此屬性,通過此屬性可爲整個類添加屬性或函數
//通過構造方法產生的Per及字面量方法對象dod都有constructor呢?系統api就這樣吧
// 4、js的對象的屬性和函數可以任意改,也可以對某個對象任意添加屬性或方法,但是如果想對所有對象都添加方法或屬性需要修改其構造方法(通過prototype屬性修改構造函數)
// 4.1 任意修改對象的屬性、函數
stu1.name = '小麗'
stu1.study = function () {
console.log('小麗在學習')
}
// 4.2 某個對象任意添加屬性或方法
// 添加屬性
stu1.age = 12;
// 添加方法
stu1.sleep = function () {
console.log(stu1.name,'在學校睡覺');
}
// 4.3如果想對所有對象都添加方法或屬性需要修改其構造方法(通過prototype屬性修改構造函數)
//爲整個類添加屬性
Student.prototype.major = '數學';
//爲整個類添加函數
Student.prototype.play = function () {
console.log('學生玩籃球');
}
//在添加屬性和函數之前創建的對象,也能調用新添加的屬性和函數
只能用類來調用prototype屬性,不能通過對象添加屬性和函數
7.18
09-js基礎-對象和麪向對象
構造函數中用prototype添加的屬性和函數與正常添加的屬性和函數對比
//結論:比較prototype創建的屬性和正常創建的屬性的地址(===),沒有可比性,因爲屬性不是對象,只是值對比
// 比較prototype創建的函數和正常創建的函數的地址 p1.eat === p2.eat;p1.run === p2.run,則說明
// prototype相當於對象的共享庫,且函數是一種object(對象),所有無論p1,p2是否重寫run方法,即使是重寫成一樣的,run函數的比較都是false
// 而無論哪種方式創建的屬性,只要屬性值一樣,則對比爲true
// 故爲了節省內存考慮,也要用prototype的形式添加函數
構造函數的終極寫法
function Person(option) {
// this.name = option.name;
// this.age = option.age;
this._init(option)
}
Person.prototype = {//字面量對象方式來寫
_init:function(option){//屬性可以這樣寫在prototype中,也可以直接寫在Person構造方法中
this.name = option.name;
this.age = option.age;
},
eat:function (something) {
console.log(this.name,'吃',something);
},
run:function (someplace) {
console.log(this.name,'go',someplace);
},
}
Js中數據類型和內存分析
棧區:編譯器自動分配釋放,存函數參數值,局部變量等
堆區:有程序員分配釋放,如果開發者不釋放,程序在結束時會回收
內存:可以理解爲棧區,放小的且常用的,基本數據類型
硬盤:可以理解爲堆區,放體積大的,複雜數據類型,有地址
Js中的數據類型:
簡單(基本)數據類型:String,Number,Boolean,Undefined,Null 存儲在棧區
複雜(引用)數據類型:Array,Object,Date 存儲在堆區
注意:堆區的東西要通過棧區來取,棧區存的是複雜類型的地址值,堆區存的是實在的複雜類型的內容
Js的內置對象:js已經創建好的對象,直接使用即可,不需要再定義了
常見內置對象:Date,Array,Math,RegExp(正則),Error,String。。。
Array高級API:1~3對數組的操作都會改變原數組 5~8不會改變原數組
1 sort() 排序,必須加回調函數控制升序排序,親測不加會有問題(課程說不加默認升序) 內部用冒泡
console.log(array.sort(function (a,b) {//[1, 4, 23, 32, 54]
return a - b;//小-》大
}))
console.log(array.sort(function (c,d) {//[54, 32, 23, 4, 1]
return d - c;//大-》小
}))
2 slice() 截取數組,倆參數
var arr1 = array.slice(1);//[1,最後]
var arr2 = array.slice(1,4);//[)
var arr3 = array.slice(1,-2)//[1,-2+array.length)
var arr4 = array.slice(-4,-1)//[-4+array.length,-1+array.length)
3 splice() 插入 刪除 修改,仨參數
刪除
var removeArr = array.splice(0,3);
插入
array.splice(2,0,'ad','sd')//從2下標開始,添加元素ad sd
刪除 插入
array.splice(2,4,'k','p');//從下標2開始刪除四個(不夠4個,則有幾個刪幾個,再加插入ad,sd)
// 清空數組
// array = [] //清空方法一
array.splice(0)//清空方法二
4 foreach() 遍歷 回調函數方式
// forEach可以避免同步異步問題???
array.forEach(function (a,b) {
console.log(a,b);//value,key
})
5 map() 映射 返回函數調用結果組成的數組
6 filter() 過濾,產生新數組
7 every() 數組中都滿足條件返回true 返回boolean
8 some() 數組中只要有滿足條件的就返回true
Js的特效-DOM BOM
Js是事件驅動型語言
事件源:標籤/document/節點
獲取事件源方法(獲取節點)
var btn = document.getElementById('btn')//id
var btn1 = document.getElementsByClassName('classbtn')[1]//類
var btn2 = document.getElementsByTagName('button')[0]//標籤
// querySelector 默認選第一符合條件的標籤 選擇器
var btn3 = document.querySelector('#btn')//id選擇器 #
var btn4 = document.querySelector('.classbtn')//類選擇器 .
var btn5 = document.querySelector('button')//標籤
//querySelectorAll
var btn6 = document.querySelectorAll('#btn')[0];
var btn7 = document.querySelectorAll('.classbtn')[1];
var btn8 = document.querySelectorAll('button')[0]
var x = document.querySelectorAll("p.intro")[0]
DOM訪問關係:
1、獲取父節點
var span = document.getElementById('span')
var node = span.parentNode
2、獲取兄弟節點
var span = document.getElementById('span')
var previous = span.previousElementSibling || span.previousSibling //不同瀏覽器獲取的方法會有區別所以用||
var next = span.nextElementSibling || span.nextSibling//不同瀏覽器獲取的方法會有區別所以用||
3、單個節點
1》第一個節點
第一個節點(兼容不同瀏覽器) firstChild firstElementChild
2》最後一個節點(兼容不同瀏覽器) lastElementChild lastChild
3》所有子節點 (兼容不同瀏覽器) childNodes children
3.1》 childNodes:注意:火狐、谷歌等高版本會把換行看做子節點
是標準屬性,返回指定元素的子元素集合;包括元素節點、屬性節點、文本節點,以上三種節點根據nodeType區分,nodeType取值分別是1、2、3;因此要獲得所有元素節點要做遍歷
var nodeListArray = new Array();
for (var i = 0;i < nodeList.length;i++){
var node = nodeList[i]
if (1 === node.nodeType) nodeListArray.push(node)
}
3.2》 children:注意:在IE6/7/8中包含註釋節點,IE6/7/8中註釋節點不要寫在裏面;新版瀏覽器多用child
補充:獲取任意兄弟節點(獲取父節點,通過父節點獲取任意兄弟節點)
DOM節點操作:
一、節點的crud:
1、創建節點 :createElement()
document.createElement('img')
2、 增加節點:append() appendChild() insertBefore()
div.append(img);
document.body.appendChild(newDiv)
div.insertBefore(img,btn)
3、 刪除節點 removeChild() remove()
通過父節點刪除 deletBtn.parentNode.removeChild(deletBtn)
自己remove deletBtn.remove()
4、 複製節點(節點自己複製自己) cloneNode(true)
cloneCode():參數是boolean類型,true深拷貝,拷貝此節點及其子節點;false淺拷貝,只拷貝此節點,不拷貝其子節點
二、節點的屬性:
1、獲取屬性
imga.src
imga.getAttribute('src')
2、設置屬性
imga.setAttribute('src','refresh3.png');
設置自定義屬性
//2.1、自定義屬性setAttribute
imga.setAttribute('src','refresh3.png');//設置哪個屬性爲哪個值
imga.setAttribute('aaa','AAA')
console.log(imga);//能打印出aaa屬性和值
//2.2、自定義屬性 .
imga.index = 1
console.log('hhh',imga)//無index屬性和其值
console.log(imga.index);//單獨打印,能打印出index,可以用
3、刪除屬性
imga.removeAttribute('aaa')
三、節點的內容
1、innerHtml
有子節點 :包括子標籤 及 各標籤內容
無子節點:
2、innerText:各子標籤的內容:只打印雙標籤的text,類似input等單標籤不會打印,當然input有另一個值表示其字符,即value
3、value:
var inpu = document.getElementsByTagName('input')[0]
inpu.value = '我是美女'
無子節點時,innerText與innerHTML相等 都是當前標籤內容
練習案例小結
點擊a標籤時避免a的herf的響應(響應方式是打開新的網頁):在a的onclick事件 return false
<a href="refresh3.png">百度一下</a>
var aad = document.getElementsByTagName('a')[0]
aad.onclick = function () {
alert('a標籤')
console.log('dfghjk')
return false//這裏是點a標籤不跳轉的關鍵
}
2、ul.getelemnt 縮小範圍:不要寫document.getelementby.. 而要把document改成最小範圍的父節點
var didd = document.getElementById('aa')
var list1 = didd.getElementsByTagName('button')
Css的屬性而不是HTML標籤屬性時,需要通過style調用
7.19
同步異步:在換膚實例中給li標籤添加自定義屬性index,從而實現點擊圖片換圖(通過此index屬性獲取圖片名稱)操作,而沒有用for循環裏的索引i,因爲for循環是異步的,在for裏通過i獲取圖片時,i值一直是最後一次的值
Input標籤
獲取焦點事件:onfocus
失去焦點事件:obblur
取整:
Math.ceil(a); //不管小數是多少,都入,取整
Math.floor(a); //不管小數是多少,都舍,取整
Math.round(a)//四捨五入
parseInt 取整數,參數可以是是number也可以是string
parseFloat 取小數,參數可以是是number也可以是string
用js改變元素的樣式:inp.className = 'red' (red是類選擇器)
css樣式的優先級,id選擇器高於class選擇器,所有如果二者同時作用,則默認是id選擇器的style,如果,想默認是類選擇器的樣式,則在此項樣式後加!important:
border-color: yellow !important;
排他思想 選項卡注意點:
//問題:for循環與事件源的同步異步問題
//解決方式一:添加屬性
for (var i = 0; i < btnList.length;i++) {
var btn = btnList[i]
console.log('iiii'+i);
btn.index = i;
btn.onclick = function () {
console.log(this.index);//0 1 2 3 4 5
}
}
//解決方式二:使用閉包
for (var i = 0; i < btnList.length;i++) {
(function (i) {
console.log('iiirri'+i);
btnList[i].onclick = function () {
console.log(i);//0 1 2 3 4 5
}
})(i);
}