作者:~小明学编程
文章专栏:JavaEE
格言:热爱编程的,终将被编程所厚爱。
目录
JavaScript的书写形式
行内式
直接嵌入到 html 元素内部
<button onclick="alert('hello')">这是一个按钮</button>
内嵌式
写到 script 标签中
<script>
alert('hello');
</script>
外部式
写到单独的 .js 文件中
<script src="helllo.js"></script>
alert('hello');
注释
单行注释 // [建议使用]
多行注释 /* */
输入输出
输入
通过在 script 当中,使用 prompt 来达到输入的效果:
<script>
prompt();
</script>
输出
1.通过alert()来输出。
2.console.log 这个是在控制台打印日志,就是在 浏览器 的控制台里面。因为 alert 弹窗的体验非常不好,比如在看剧的时候,突然弹窗,就会暂停所有操作:
<script>
console.log('hello');
</script>
同时,如果 JS 代码当中出现错误,或者运行时错误的时候,也会在控制台当中打印出来
JS的语法规则
变量
定义变量的时候,通过 var 变量名 = 初始值;
来完成变量的定义:
<body>
<script>
//创建一个名字为 num 的,数字类型的变量
var num = 10;
//创建一个名字为 s 的,字符串类型的变量
var s = 'hello';
//创建一个名字为 arr 的,数组类型的变量
var arr = [];
</script>
</body>
就是不管创建的变量是啥类型,此时都是统一使用 var 关键字来表示的。JS 不区分整形浮点型之类的。
<script>
var a = 10;
a = 20;
console.log(a);
</script>
不过在赋值的时候,可以赋一个数字类型,也可以赋一个字符串类型。变量的类型,可以在运行过程中,随着赋值发生改变,就是 动态类型。
关于var和let:
- var 没有作用域限制。
- let 有作用域限制。
- let 的字符串和数字相加,就i是拼接字符串。
数据类型
number: 数字. 不区分整数和小数.
boolean: true 真, false 假.
string: 字符串类型.
undefined: 只有唯一的值 undefined. 表示未定义的值.
null: 只有唯一的值 null. 表示空值
数字类型
let a = 07; // 八进制整数, 以 0 开头
let b = 0xa; // 十六进制整数, 以 0x 开头
let c = 0b10; // 二进制整数, 以 0b 开头
特殊的数字值:
Infinity: 无穷大, 大于任何数字. 表示数字已经超过了 JS 能表示的范围.
-Infinity: 负无穷大, 小于任何数字. 表示数字已经超过了 JS 能表示的范围.
NaN: 表示当前的结果不是一个数字.
字符串类型
-
字符串 可以通过单引号定义,也可以通过双引号定义。
-
如果字符串本身就包含了 引号 这个时候,就可以通过 单双引号 灵活搭配的形式,来避免使用转义字符。
<script>
let str = "'hello'";
console.log(str);
</script>
JS中的转义字符,不仅仅是 +单双引号,还有其它的转义字符,也是支持的。 像 \t(水平制表符),\n(换行符),\f(换页符)…这些转义字符,也是同样支持的。
3.求字符串的长度:
<script>
let str = "hello";
console.log(str.length);
</script>
4.字符串的拼接:
js中通过+来进行字符串的拼接,同时里面也会有很多的关于字符串的方法。
<script>
let str = "hello";
str += " world"
console.log(str);
</script>
布尔类型
与 Java 中的 boolean 类型不同,JS 当中的 布尔类型,会当成 0 和 1 来处理。true 是 1,false 是 0,举一个极端例子:
<body>
<script>
let s = true;
console.log(s + 1);//2
</script>
</body>
如果一个编程语言,越支持隐式类型转换,就认为类型越弱。
如果一个编程语言,越不支持隐式类型转换,就认为类型越强。
Java,Go,Python 认为是强类型的编程语言。
C,JS,PHP 认为是弱类型的编程语言
运算符
JS 中的运算符和 Java 用法基本相同,这里拿一些不同的来说。
算数运算符:
我们需要注意JS中的/的运算,JS中是不区分整数和浮点数的所以1/2=0.5。
比较运算符:
JS中比较相等的符号,有两种:== 和 === 。不相等的符号也有两种: != 和 !== 。
1.== 和 != :只是比较两个变量的值,不比较 两个变量的类型。如果两个变量能够通过隐式类型转换,转换相同的值,那么,此时就认为 两个变量 是相等的。
2.=== 和 !== :既要比较 两个变量的值,又要比较两个变量的类型。如果类型不相同,就直接认为两个变量不相等。
<body>
<script>
let a = 10;
let b = '10';
console.log(a == b);
console.log(a === b)
</script>
</body>
逻辑运算符:
&& 和 || 和 Java 当中的不一样,Java 就是返回一个布尔类型的值: true,或者 false。而 JS 是返回其中的表达式。
c = a || b,如果 a 的值为真,那么 c 的值,就是 表达式a 的只。如果 a 的值为假,b 的值为真,那么 c 的值就是 表达式b 的值。&& 也是这种用法。
数组
使用new的关键字来创建数组
<script>
let arr = new Array();
</script>
其它创建数组的方法
<script>
let arr = [];
let arr1 = [1,2,3,4,5];
</script>
打印数组
<script>
let arr = [1,23,'a','dfsf'];
console.log(arr);
</script>
JS支持这种大杂烩的写法,同时打印数组的话直接用console.log()就可以了。
获取数组的元素
<body>
<script>
let arr = [1,2,3,4];
console.log(arr[0]);
console.log(arr[1]);
</script>
</body>
按照 Java 的话,超出数组长度的话,就会抛出异常,但是 JS 不会,而是抛出 undefined :
<body>
<script>
let arr = [1,2,3,4];
arr[100] = 10;
arr[-1] = 11;
arr['hello'] = 13;
console.log(arr);
</script>
</body>
其中-1下标和hello这种可以看作是数组的一个元素,其中并不影响数组的长度。
数组的长度
通过 .length
来获取数组长度:
<script>
let arr = [1,2,3,4];
arr[100] = 10;
arr[-1] = 11;
arr['hello'] = 13;
console.log(arr);
console.log(arr.length);
</script>
其中值得我们注意的是JS 里面的 length 属性是可以修改的:当改变后的长度小于原有的长度的自动删除后面的长度,当大于原有的长度的时候多余的就为空。
向数组中插入元素
通过 push 方法,来往数组当中插入新的元素:
<body>
<script>
let arr = [1,2,3,4];
arr.push(5);
console.log(arr);
</script>
</body>
删除元素
通过 splice 方法,就可以对数组中的某个片段,进行替换(因为是替换,所以可以看作是删除元素)
<body>
<script>
let arr = [1,2,3,4];
arr.splice(2, 2);
console.log(arr);
</script>
</body>
这里的意思就是:从下标为 n 的元素,向后删除 n 个元素,就是从下标为 2 的元素,向后删除 2 个元素,运行结果如下:
函数
JS 中的函数(function),在 Java 中叫做 方法(Method)。函数就是方法,方法就是函数,两者就是同一个东西,只是叫法不同而已。
语法格式
// 创建函数/函数声明/函数定义
function 函数名(形参列表) {
函数体
return 返回值;
}
// 函数调用
函数名(实参列表) // 不考虑返回值
返回值 = 函数名(实参列表) // 考虑返回值
不过要注意的是,在 创建函数/函数声明/函数定义 的时候,形参列表不用写形参类型。因为参数类型,完全取决于调用的时候,传什么参数。代码:
<script>
function hello() {
console.log('hello');
}
hello();
</script>
无参数类型
<script>
function add(x, y) {
return x + y;
}
let result = add(10, 20);
console.log(result);
result = add('hello','world');
console.log(result);
result = add('hello', 10);
console.log(result);
</script>
function add(a, b, c, d, e, f, g) {
a = a || 0;
b = b || 0;
c = c || 0;
d = d || 0;
e = e || 0;
f = f || 0;
g = g || 0;
return a + b + c + d + e + f + g;
}
console.log(add(10, 20));
console.log(add(10, 20, 30));
console.log(add(10, 20, 30, 40));
函数表达式
在 JS中,函数是 “一等公民”。一个“一等公民”的函数,函数可以像一个普通的变量一样,赋值给 其他的变量。同时,可以作为另一个函数的参数,还可以作为另一个函数的返回值。简单来说:函数和普通的变量,并没有本质区别。只不过函数这个变量,相对于普通变量来说,多了一个功能(可调用)。
<script>
function test() {
console.log('hello');
}
let f = test;
f();
</script>
test 是一个函数名,test 后面没有(),说明这个操作,不是函数调用,而是一个单纯的函数的赋值。f 是一个 function 类型的变量。
匿名函数
<script>
let f = function() {
console.log('hello');
}
</script>
匿名函数也就是 lambda 表达式。
作用域
所谓作用域就是某个标识符名字在代码中的有效范围。在 ES6 标准之前, 作用域主要分成两个:
- 全局作用域: 在整个 script 标签中, 或者单独的 js 文件中生效。
- 局部作用域/函数作用域: 在函数内部生效.
其实在 ES6 之前,就没有 let 这个东西。let 是在 ES6之后 才引入的。在ES6版本之前,只有 var。在ES6版本之前,只有 var。在 JS 中,{}内部代码 是可以访问 {} 外部的代码的。:
<body>
<script>
let num = 32;
{
console.log(num);
}
</script>
</body>
<body>
<script>
let num = 60;
function hello() {
console.log(num);
}
hello();
</script>
</body>
同样我们也可以在函数的内部访问。
对象
所谓对象就是一些属性 和 方法的集合。与传统意义上的Java对象的概念是类似的。
在 JS 中,对象 是不依托于 类的。直接通过 {} 就可以创建对象
创建对象:
js对象中的每个属性和方法,其实都是通过“键值对” 这样的方式来表达的。{} 表示这是一个对象。
- 键值对之间,采用 逗号 进行分割。
- 键和值之间,采用 冒号 进行分割。
- 后续就可以通过 对象名 . 来访问了
使用字面量创建对象
<script>
var student = {
name:'ikun',
height:175,
weight:125,
sing:function(){
console.log('ctrl');
}
}
console.log(student.name);
console.log(student.sing());
</script>
使用new object()创建对象
<script>
var student = new Object(); // 和创建数组类似
student.name = "蔡徐坤";
student.height = 175;
student['weight'] = 170;
student.sayHello = function () {
console.log("hello");
}
console.log(student.name);
console.log(student['weight']);
student.sayHello();
</script>
使用构造函数创建对象
function 构造函数名(形参) {
this.属性 = 值;
this.方法 = function...
}
var obj = new 构造函数名(实参);
在构造函数内部使用 this 关键字来表示当前正在构建的对象.
构造函数的函数名首字母一般是大写的.
构造函数的函数名可以是名词.
构造函数不需要 return
创建对象的时候必须使用 new 关键字.
DOM API
对于在浏览器上运行的 JS 来说,最核心的库,就是 DOM API。
DOM API 是浏览器给 JS 提供的原生接口。基于这样的接口,就可以针对页面上的元素进行操作了。
DOM ->Document 0bject Model - 文档对象模型。
文档指的是页面显示的部分。对象指的是 JS中代码操作的部分。
JS 这边操作 对象,文档那边就会发生改变。所以 这两个的关系,是相辅相成的关系。
不过原生的 DOM API 能用,但是并不方便。所以也就有了大量的第三方库/框架。像 JQuery 就是一个知名的库。
querySeletor
获取元素
通过 querySelector 来获取页面参数:
<body>
<div class="one">
hello
</div>
<script>
//选择元素
let div = document.querySelector('.one');
console.log(div);
</script>
</body>
通过#获取
<div id="one">
hello
</div>
<script>
//选择元素
let div = document.querySelector('#one');
console.log(div);
</script>
querySelectorAll
使用 querySelectorAll 就是选中所有元素,然后返回一个数组。准确的说 querySelectorAll 返回的并不是一个数组,而是一个对象,只不过有 length,而且可以通过 下标来访问内部因素,使用起来和数组非常相似(一模一样),就是叫做”伪数组“:
<body>
<ul>
<li>hello1</li>
<li>hello2</li>
<li>hello3</li>
<li>hello4</li>
<li>hello5</li>
</ul>
<script>
//选择元素
let div = document.querySelectorAll('ul li');
console.log(div);
</script>
</body>
事件
就是浏览器对于 用户操作 行为就行的 统称,大部分是用户操作产生的:
- 鼠标在页面上移动,就会产生一个鼠标移动事件
- 鼠标点击页面某个位置,就会产生一个鼠标点击事件
- 鼠标滚动,也是一个事件
JS 主要就是在不同的事情中,进行不同的处理,事件的三个要素:
- 事件源:哪个 HTML 产生的事件,JS 中的很多代码,都是通过 事件 来触发。
- 事件类型:鼠标移动,点击,键盘事件,窗口大小改变事件
- 事件的处理程序:事件产生之后,执行什么样的 JS 代码
<button>这是一个按钮</button>
<script>
let button = document.querySelector('button');
button.onclick = function() {
alert('hello');
}
</script>
操作元素内容
<body>
<div id="screen">hello world</div>
<button id="btn">这是一个按钮</button>
<script>
let btn = document.querySelector('#btn');
btn.onclick = function () {
let screen = document.querySelector('#screen');
console.log(screen.innerHTML);
}
</script>
</body>
<div id="screen">
<ul>
<li>aaa</li>
<li>aaa</li>
<li>aaa</li>
</ul>
</div>
<button id="btn">这是一个按钮</button>
<button id="btn2">这是修改后的内容</button>
<script>
let btn = document.querySelector('#btn');
btn.onclick = function() {
let screen = document.querySelector('#screen');
console.log(screen.innerHTML);
}
let btn2 = document.querySelector('#btn2');
btn2.onclick = function() {
let screen = document.querySelector('#screen');
screen.innerHTML = '<h1>修改后的内容';
}
</script>
<div id="screen">
0
</div>
<button id="plus">+</button>
<script>
let plusBtn = document.querySelector('#plus');
plusBtn.onclick = function() {
let screen = document.querySelector('#screen');
let val = screen.innerHTML;
val = parseInt(val);
val += 1;
screen.innerHTML = val;
}
</script>
操作元素属性
<img src="1.jpg" alt="">
<script>
let img = document.querySelector('img');
img.onclick = function() {
console.log(img.src);
if(img.src.indexOf('1.jpg')>=0) {
img.src = '2.jpg';
} else if (img.src.indexOf('2.jpg') >=0) {
img.src = '1.jpg';
}
}
</script>
我们刷新一下页面
点击之后:
通过 dom 对象 . 属性名就可以操作了。一个 HTML 标签里,能写哪些属性,就同样可以通过 JS 中的 DOM 对象来获取到一样的属性。
切换按钮的显示文本
<input type="button" value="播放">
<script>
let input = document.querySelector('input');
input.onclick = function () {
if (input.value == '播放') {
input.value = '暂停';
} else if (input.value == '暂停') {
input.value = '播放';
}
}
</script>
实现全选按钮
<input type="checkbox" id="all"> 全都要 <br>
<input type="checkbox" class="ch">苹果 <br>
<input type="checkbox" class="ch">西瓜 <br>
<input type="checkbox" class="ch">梨 <br>
<input type="checkbox" class="ch">香蕉 <br>
<script>
// 实现全选表单的效果
// 1、获取元素
let all = document.querySelector('#all');
let ch = document.querySelectorAll('.ch');
//2、给 all 注册点击事件
all.onclick = function () {
for (let i = 0; i < ch.length; i++) {
ch[i].checked = all.checked;
}
}
// 3、针对每个 ch 注册点击事件,实现对 all 的取消操作
for (let i = 0; i < ch.length; i++) {
ch[i].onclick = function () {
all.checked = checkCh(ch);
}
}
function checkCh(ch) {
//判断是不是所有的 ch 都被选中
for (let i = 0; i < ch.length; i++) {
if (!ch[i].checked) {
//只要有一个没被选中,就让 all 是未选中状态
return '';
}
}
//遍历一圈,发现都被选中了,就让 all 也是选中状态
return 'checked';
}
</script>
操作元素样式
本质上也是操作元素属性:
- style 对应行内样式(直接把样式写到 style 里面)
- className/classList 对应内部样式/外部样式 应用了 一个/一组 CSS 类名
style 操作示例:点击放大字体:
<body>
<div style="font-size: 20px">这是一个文本</div>
<script>
let div = document.querySelector('div');
div.onclick = function () {
//先获取到当前字体大小
let fontsize = parseInt(div.style.fontSize);
//在当前字体大小基础上,增加 5px
fontsize += 5;
div.style.fontSize = fontsize + 'px';
}
</script>
</body>
随着点击字体就变得越来越大。
实现开关灯的效果:
<style>
.light {
background-color: white;
color: black;
}
.dark {
background-color: black;
color: white;
}
</style>
<div class="light" style="height: 500px">这是一段话</div>
<button>关灯</button>
<script>
let div = document.querySelector('div');
let button = document.querySelector('button');
button.onclick = function () {
if (div.className == 'light') {
div.className = 'dark';
button.innerHTML = '开灯';
} else if (div.className == 'dark') {
div.className = 'light';
button.innerHTML = '关灯';
}
}
</script>
操作节点
新增节点
<body>
<div class="container"></div>
<script>
//1、创建新节点
let newDiv = document.createElement('div');
newDiv.id = 'newDiv';
newDiv.className = 'one';
newDiv.innerHTML = 'hello';
console.log(newDiv);
//2、把节点挂在 dom 树上
let container = document.querySelector('.container');
container.appendChild(newDiv);
</script>
</body>
删除节点
通过 removeChild 来实现,先拿到父节点,然后再拿到待删除的子节点:
<body>
<div class="container"></div>
<button>删除 div</button>
<script>
//1、创建新节点
let newDiv = document.createElement('div');
newDiv.id = 'newDiv';
newDiv.className = 'one';
newDiv.innerHTML = 'hello';
console.log(newDiv);
//2、把节点挂在 dom 树上
let container = document.querySelector('.container');
container.appendChild(newDiv);
//删除
let button = document.querySelector('button');
button.onclick = function () {
container.removeChild(newDiv);
}
</script>
</body>
实战用法
猜数字游戏
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>猜数字游戏</title>
</head>
<body>
<button id="resetBtn">重新开始游戏</button><br>
<span>要猜的数字</span>
<input type="text">
<button id="guessBtn">猜</button><br>
<span>结果:</span><span id="result"></span><br>
<span>已经猜的次数</span>
<span id="guessCount">0</span>
<script>
//1.拿到要用的元素
let resetBtn = document.querySelector('#resetBtn');
let input = document.querySelector('input');
let guessBtn = document.querySelector('#guessBtn');
let resultSpan = document.querySelector('#result');
let guessCountSpan = document.querySelector('#guessCount');
//2.生成一个1-100的随机数
let toGuess = Math.floor(Math.random() * 100)+1;
console.log(toGuess);
//3.实现猜的逻辑
guessBtn.onclick = function() {
if (input.value == '') {
return;
}
let curNum = parseInt(input.value);
if(curNum<toGuess) {
resultSpan.innerHTML = '猜小了';
resultSpan.style.color = 'red';
} else if(curNum>toGuess) {
resultSpan.innerHTML = '猜大了';
resultSpan.style.color = 'red';
} else {
resultSpan.innerHTML = '猜对了';
resultSpan.style.color = 'green';
}
let guessCount = parseInt(guessCountSpan.innerHTML);
guessCountSpan.innerHTML = guessCount +1;
}
resetBtn.onclick = function() {
location.reload();
}
</script>
</body>
</html>