WEB技术与应用课程

Web技术与应用课程

一、Java Script:

1.引入script代码:

1
2
3
<script>
<!---javascript 代码--->
</script>

2.引入外部script代码

1
2
<script src = "externalJS.js">
</script>

3.定义变量:

(1)赋值定义:

1
2
3
4
var i = 123;
var str = "Hello";
var str1 = 'abc';
var phr = \`abc\${str}`;//(使用这种类型插入其他的字符)

(2)未赋值,初始化类型

1
2
var i;
typeof i = 'undefined';//(这种类型被判定为False)

▲javaScript的浮点数操作不一定准确:

0.1+0.2 = 0.300000…..04

通常使用(0.1x10+0.2x10)/10的形式

在其他语言中也通常存在的

(3)特殊类型

null和undefined的值相等,但是类型不一样,null的类型是object

4.定义函数

(1)初始定义

function function_name(){ ……. }

没有定义返回值的函数也会返回Undefined的类型。

(2)传参定义

①定义function func(){…}

仍然可以调用func(a,b,c)这种类型,传入的参数a,b,c被存放在arguments这个数组中,全局的数组。

②定义function func(x){ return x}

可以调用func(),不传参,如果返回的是undefined类型的

(3)定义的hoisted

即函数可以定义在使用之后,应该是编译的时候进行了提升操作

变量也具有这个效果,比如在同一个函数下的所有变量的作用域都是这个函数,但是其值并没有得到提升。

函数变量的toString就是函数的定义表达式

(4)strict模式

当函数定义中,加入了”use strict”时,会对变量的声明有更严格的要求,不能简单地直接赋值。

(5)non-hoisting模式

(6)Let关键字

1
2
3
var x = 10

{let x = 2}

let使得x只在{…}这个声明块中有效,外面的语句中x的值为10。

5.定义对象

(1)初始赋值

1
2
let user = {name:"Alice",age:23,country:"China"};
var d = new Date();//(日期对象)

(2)增加属性

1
user.fan = "Banana";

(3)删除属性

1
delete user.name;

(4)遍历对象

1
2
Object.keys(user);
Object.values(user);

获取变量的key和values的相关数据

6.定义数组(类型为object)

(1)初始定义

1
var anArr = [1,2,3];

(2)相关操作

1
2
3
anArr[5] = "FooBar";//(这个也是可以的)
anArr.length;//返回值为6
anArr.sort();//排序相关

(3)数据结构相关操作

①尾部操作

1
2
anArr.push();
anArr.pop();

②首部操作

1
2
anArr.shift();
anArr.unshift();

(4)filter方法

创建新数组检测原数组

1
2
3
4
5
6
7
8
var ages = [33,32,16,40];
function checkAdult(age){
return age >= 18;
}
console.log(ages.filter(checkAdult));
console.log(ages.filter(function(value){
return value >= 18;
}))

7.正则表达式

(1)定义正则表达式

1
2
var re = /ab+c/;//(使用两个/来定义正则)
var re2 = new RgeExp("ab+c");//(使用对象来定义正则)

(2)调用正则

①字符串形式

1
"XXXXXXX abbbbc".search(/ab+c);

返回值为查找到的索引,没找到则返回-1

②对象调用

1
2
var re = /ab+c/;
re.exec(str);//返回re这个表示式的执行结果,返回包含结果的一个数组

(3)模式

...表任意字符

+至少一个

*0个或多个

?0个或多个

\d找一个数字 (digtal)

\s找一个空格 (space)

\b找一个单词的开始或结尾

g全局模式,在表达式末尾加上g代表全局,返回所有查找到的

比如匹配abbbc即可用ab+c

var re3 = /[^\d]/;表查找不是数字的

8.异常处理

1
2
3
4
5
6
7
8
try{
Block of code....
throw "Help!";
}catch(err){
console.log("Error call");
}finally{
will be exec whatever there are some error....
}

9.Debug

在chrome中可以调试,即浏览器

10.新的特性

(1)Modules

1
2
3
4
5
6
7
8
9
10
//profile.js
var a = "aa";
var b = "bb";
export {a,b};

//main.js
import {a,b} from './profile.js';
function setName(element) {
element.textContent = a + ' ' + b;
}

(2)Default para

1
2
3
function myFunc(a=1,b="Hello"){

}

digtal + undefined = NaN

(3)Rest para

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
//the ArgsArray放置的是多余的参数
function myFunc(a,b,... the_ArgsArray){
var c=the_ArgsArray[0];
}


function add(...values) {
let sum = 0;
for (var i=0;i<values.length;i++) {
sum += values[i];
}
return sum;
}
//2,5,3被放置在values数组中
add(2, 5, 3) //返回10

(4)spread operator

1
2
3
var anArray=[1,2,3];
myFunc(...anArray);//将数组anArray的每个元素作为函数参数传给myFunc函数
var o=[5,...anArray,6];

(5)模板类字符串string

1
2
3
4
function formatGreetings(name,age){
var str=
`Hi ${name} your age is ${age}`;
}//新特性字符串的拼接

(6)遍历

1
2
3
4
let sum=0;
for(ent of a){
sum+=ent;
}

11.类和对象

(1)声明和添加

1
2
3
4
5
6
7
let o = {oldProp:'old'};
o.aMethod = function(){
this.newProp = 'new';
return Object.keys(this);
}
o.aMethod();
//o的成员即为[oldProp,newProp,aMethod]

(2)函数即为对象

1
2
3
4
5
6
7
8
9
function func(value){
console.log(this,arg);
}
func.toString();
func.call({t:1},2);
//call使得func这个对象就会变成{t:1}
let newFunc = func.bind({z:2},3);
//bind会返回一个新的对象为{z:2}
//所有对象都有toString,call,bind等方法

(3)定义类和实例化

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
function Rectangle(width,height){
this.width = width;
this.height = height;
this.area = function(){
return this.width*this.height;
}
}
var obj = new Rectangle(26,14);

//查看objd的构造方法是不是'Rectangle'
obj.constructor.name == 'Rectangle'

//给Obj增加属性description
obj.description = 'big Rectangle';

var obj2 = new Rectangle(2,3);
obj2.tell = function(){
alert(width+";"+height);
}
//以上方法增加的属性在对象里,不在类里

console.log(obj);
console.log(obj2);

(4)为类增加属性方法

1
2
3
4
5
6
7
8
9
10
11
function Rectangle(width,height){
this.width = width;
this.height = height;
}

//使用prototype给Rectangle这个类增加成员
Rectangle.prototype.area = function(){
return this.width*this,height;
};
Rectangle.prototype.description = 'Hello!';
//这种方法相当于修改类的定义,所有的实例化对象都会被修改掉

(5)新版的类

1
2
3
4
class shape(){
constructor(str){this.str = str};
}
class Rectangle extends shape = ...

12.函数式编程

(1)处理字符串

1
2
3
4
5
6
7
8
9
10
11
var anArr = [45,4,9,16,25];
function filterFunc(value){
return value<45;
}
function mapFunc(value,idx){
return value*idx;
}
function reduceFunc(total,value){
return total+value
}
anArr.filter(filterFunc).map(mapFunc).reduce(reduceFunc)

(2)回调函数

主要用来跟踪异步的函数调用行为,确保正常异步加载结束

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
<body>
<script>
//可以异步调用该函数,使得该函数后面的其他脚本也同时运行
function loadScript(src){
let script = document.createElement('script');
scripte.src = src;
document.head.append(script);
}
loadScript('./myScript.js');
newFunction();
//当newFunction()在myScript.js中时,如果myScript.js没有加载完,则直接调用
//newFunction会出错,因为没有加载上


//使用回调函数确保脚本加载完成再调用其中的函数
function callbackFunc(){
newFunction();
}
function loadScript(src,callback){
let script = document.createElement('script');
scripte.src = src;
script.onload = () => callback(script);
document.head.append(script);
}
loadScript('./myScript.js');
//这样在loadScript函数执行完成之后才会执行callbackFunc从而调用newFunction

//3*1000毫秒后执行callbackFunc
setTimeout(callbackFunc,3*1000)

//读完文件之后再调用callbackFunc
function callbackFunc(err,data){
console.log(String(data));
}
fs.readFile('/etc/passwd',callbackFunc);

</script>
</body>

▲注

方法:代表对象里面的函数

函数:对象外部的函数

(3)闭包

即在调用函数对象内部的函数,该函数修改函数对象内的成员,该成员可以得到修改使用,就类似于java中的接口设置。

1
2
3
4
5
6
7
8
var myObj = (function() {
var privateProp1 = 1;
var privateProp2 = "test";
var setPrivate1 = function(val1) { privateProp1 = val1; }
var compute = function() {return privateProp1 + privateProp2;}
return {compute: compute, setPrivate1: setPrivate1};
})();
//即可以通过接口函数setPrivate1和compute来访问其privateProp1和privateProp2

13.类型判断

==:只判断值,false和false比较都为true…

===:判断类型和值

14.Promise替代回调函数

将执行结果保存,然后利用函数处理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
//等待1秒后执行resolve,将结果给到promise.result中
let promise = new Promise(function(resolve, reject) {
setTimeout(() => resolve("done!"), 1000);
});


//一般用来处理promise的执行结果
promise.then(
result => alert(result), // shows "done!" after 1 second
error => alert(error) // doesn't run
);

//catch只处理错误结果
promise.catch(error);

加载脚本的处理

1
2
3
4
5
6
7
8
9
10
function loadScript(src) {
return new Promise(function(resolve, reject) {
let script = document.createElement('script');
script.src = src;
script.onload = () => resolve(script);
script.onerror = () => reject(new Error(`Script load error for ${src}`));
document.head.append(script);
});
}
loadScript(src).then(func...);

15.async/await语法

async异步执行

defer标志后浏览器完全解析完才会执行script代码

经常加入 async和defer来使得异步加载dom树,从外部引入javascript代码

二、JSON

JSON即JavaScript对象数据的存储形式,也用来发送数据

1.基本语法

(1)转换

①对象转JSON字符串

1
2
var myJSON = JSON.stringify(obj);
typeof myJSON = 'string';

②JSON字符串转对象

1
2
3
var s='{ "name":"John", "age":30, "city":"New York"}';
var myobj=JSON.parse(s);
typeof myobj=='object';

三、DOM树

文档对象模型

以文件夹树的形式进行存储,依据文档生成DOM树

1
2
3
4
5
6
7
8
9
<html>
<head>
<title> My title </title>
</head>
<body>
<a href="a.html" > My link </a>
<h1> My header </h1>
</body>
</html>

以上代码即可形成以下的DOM树

image-20211125115502855

通常进行结点修改信息

1.基本语法

(1)获取属性

①通过body

1
element = document.body.firstChild.nextSibling.firstChild;

比如以下结构

1
2
3
4
5
6
7
8
9
10
11
12
13
<html>
<body>
Test

<div>Users:</div>
<ul>
<li>John</li>
<li>Pete</li>
</ul>

Final
</body>
</html>

寻址div结点

1
divNote = document.body.firstChild.nextSibling

②通过ID

1
<p>Sample<b id="mb">bold</b>display</p>

以上形式的b结点可通过其ID查找

1
bNote = document.getElementById('mb')

③其他查找形式

以下方法均返回一个数组

A.tagName
1
2
3
4
5
<body>
<p>Hello</p>
<p>Hello P</p>
<p>Hello DOM</p>
</body>

查找:

1
var tagPArr = document.getElementsByTagName("p")//得到三个结点标签p的数组tagPArr
B.className
1
2
3
4
5
6
7
8
<div class="example">
A div element with class="example"
</div>
<div class="example">
Another div element with class="example"
</div>
<p class="example">A p element with
class="example"</p>

查找:

1
2
var classExampleArr = document.getElementsByClassName("example")
//得到三个结点class为example的数组
C.选择符查找

获取所有标签为”p”的结点,返回得到一个数组

1
var myNodelist = document.querySelectorAll("p");

(2)设置属性

①常规修改

1
2
3
4
5
6
7
8
9
10
11
<script>
var op=document.getElementById("mp");
console.log(op.textContent);//Samplebolddisplay
console.log(op.innertHTML);//Sample<b>bold</b>display
console.log(op.outerHTML);
//<p id="mp">Sample<b>bold</b>display</p>
op.setAttribute("class","cp");
op.className = "active";
//css结构属性修改
op.style.//....
</script>

(3)插入新结点

1
2
3
4
5
6
//先生成标签为P的结点
para = document.creatElement("P");
//生成文本字符为My Text的结点
node = document.creatTextNode("My Text");
//将文本结点放到para里,形成 <p>My Text</p> 这样的结点
para.appendChild(node);

(4)布局属性

得到元素在当前页面中的坐标

image-20211130111349453

①获取布局信息

position:

relative即代表设置为可定位的

absolute代表以最近设置过postion的元素为基准,往上层找元素

不设置postion状态则依次排列

1
2
3
//元素需要先是定位过的,即position属性被设置
//如果没有定位,则默认offsetParent为body元素
var ofH = element.offsetHeight;

②设置布局信息

1
2
element.style.position = "absolute";
element.style.left = "40px";

(5)事件处理

①添加事件处理

A.直接定义
1
2
3
4
5
6
7
8
9
10
11
12
13
<div onclick="gotMouseClick('id42');">...</div>

//直接处理语句为"this.innerHTML = 'Ooops!'"
<h1 onclick="this.innerHTML = 'Ooops!'"> </h1>


<!--HTML中直接定义函数处理-->
<h1 onclick="changeText(this)"> </h1>
<script>
function changeText(id) {
id.innerHTML = "Ooops!";
}
</script>
B.DOM定义
1
2
3
4
5
6
//获取元素之后添加对应的处理事件
element.onclick = mouseClick;

//或者
element.addEventListener("click", mouseClick);
element.removeEventListener.....

②获取事件相关信息

1
2
//在事件函数中的处理,event即为当前事件的对象
console.log(event.timeStamp);

③多事件处理相应顺序

A.冒泡处理方式 Bubbling
1
2
3
4
5
<form onclick="alert('form')">FORM
<div onclick="alert('div')">DIV
<p onclick="alert('p')">P</p>
</div>
</form>

从里向外处理,即p->div->form顺序处理相应事件

B.停止冒泡处理

到form处理时停止传播

1
2
3
4
5
6
<form 
onclick="event.stopPropagation()">FORM
<div onclick="alert('div')">DIV
<p onclick="alert('p')">P</p>
</div>
</form>
C.从外层向内处理 Capture

每个标签均添加鼠标点击处理事件,alert()函数的捕获状态为true和false

true:设置捕获状态为true,使其处理从外向内处理

fasle:设置捕获状态为false,使其处理从内向外处理

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<style>
body * {
margin: 10px;
border: 1px solid blue;
}
</style>
<form>FORM
<div>DIV
<p>P</p>
</div>
</form>
<script>
for(let elem of document.querySelectorAll('*')) {
elem.addEventListener("click",
e => alert(`Capturing: ${elem.tagName}`), true);
}
</script>

停止处理也是一样的,添加stopPropagation事件

🔺W3C形式为先Capture再Bubbling的综合形式

④事件的目标

⑤时间相关的事件

1
2
3
setTimeout(func,50);
token = setInterval(func,50);
clearInterval(token);

⑥事件的线程

单线程处理事件,不会同时执行多个事件。若存在回调函数时,也是顺序进行处理的,顺序可能会不太一样。

四、BOM树

浏览器中的对象树

navigator screen location history

1.基本语法

(1)常见对象

1
2
3
4
5
6
7
8
9
//location即当前页面的html文件指针
window.location.href = "newPage.html";

//history保存用户访问过的页面,以下为执行回退上一个页面指令
window.history.go(-1);
history.go(-3); // Go back three pages
history.go(3); // Go forward three pages
history.back(); // Same as history.go(-1)
history.forward();// Same as history.go(1)

image-20211130111020329

▲注:dom和script顺序生成问题

render tree是渲染的

script会影响dom树的构建,html中在script之后的dom树结构不会在script中存在。

五、多代Web技术

1.无状态

即不保存用户信息

2.第一代

PHP,ASP,.net等应用

3.第二代

Ruby on Rails,Django等

创建model-view-controllers , Templates等

Model:

大多是Java Script的对象

View:

HTML/CSS等

最终呈现给用户的Web框架,HTML加上其他的一些代码

Controller:

按钮控建等

在服务器中获取model进行处理,将页面呈现出来,常见的Java Script的执行代码

4.第三代

Angular JS

更加类似app。

5.第四代

通过虚拟的DOM树来形成页面

React小项目:

I Love You ❤️ (pig-007.github.io)