JavaScript基础学习

news2024/9/20 1:03:29

文章目录

  • 什么是JavaScript
      • JavaScript 运行过程
      • JvaScript 的组成
  • JavaScript的三种书写模式
      • 行内式
      • 内嵌式
      • 外部式
  • JavaScript的输出输出方式
      • 输入: prompt
      • 输出: alert
      • 输出: console.log
  • JavaScript的一些基础语法
      • 变量的使用
      • 如何理解JS的动态类型(弱类型)
    • 基本数据类型
      • number 数字类型
      • string字符串
      • boolean
      • undefined 未定义数据类型
      • null 空值类型
      • 关于相等的细节
    • 数组
      • 创建数组
      • 获取数组元素
      • 新增数组元素
      • 删除数组中的元素
    • 函数
      • 语法格式
      • 关于参数个数
      • 函数表达式
      • 作用域
      • 作用域链
    • 对象
      • 定义对象的方法
      • JavaScript 对象不区分 "属性" 和 "方法"
      • JavaScript 对象没有 private / public 等访问控制机制.
      • JavaScript 没有 "类" 的概念
      • JavaScript 对象没有 "继承"
      • JavaScript 没有 "多态"
  • WebAPI
    • 什么是 WebAPI
    • DOM 基本概念
      • 什么是 DOM
      • DOM 树
      • 获取元素
    • 事件初识
      • 基本概念
      • 事件三要素
    • 操作元素
      • 获取/修改元素内容
      • 获取/修改元素属性
      • 获取/修改表单元素属性
      • 获取/修改样式属性
    • 操作节点
      • 新增节点
      • 插入节点到 DOM树中
      • 删除节点

什么是JavaScript

JavaScript (简称 JS)

  • 是世界上最流行的编程语言之一
  • 是一个脚本语言, 通过解释器运行
  • 主要在客户端(浏览器)上运行, 现在也可以基于 node.js 在服务器端运行.

JavaScript 的能做的事情:

  • 网页开发(更复杂的特效和用户交互)

  • 网页游戏开发

  • 服务器开发(node.js)

  • 桌面程序开发(Electron, VSCode 就是这么来的)

  • 手机 app 开发

JavaScript 运行过程

  • 编写的代码是保存在文件中的, 也就是存储在硬盘(外存上).
  • 双击 .html 文件浏览器(应用程序)就会读取文件, 把文件内容加载到内存中(数据流向: 硬盘 => 内存)
  • 浏览器会解析用户编写的代码, 把代码翻译成二进制的, 能让计算机识别的指令(解释器的工作)
  • 得到的二进制指令会被 CPU 加载并执行(数据流向: 内存 => CPU)

在这里插入图片描述

浏览器分成渲染引擎 + JS 引擎.

  • 渲染引擎: 解析 html + CSS, 俗称 “内核”
  • JS 引擎: 也就是 JS 解释器. 典型的就是 Chrome 中内置的 V8,JS 引擎逐行读取 JS 代码内容, 然后解析成二进制指令, 再执行.

JvaScript 的组成

  • ECMAScript(简称 ES) : JavaScript 语法
  • DOM: 页面文档对象模型, 对页面中的元素进行操作
  • BOM: 浏览器对象模型, 对浏览器窗口进行操作

光有 JS 语法, 只能写一些基础的逻辑流程.
但是要想完成更复杂的任务, 完成和浏览器以及页面的交互, 那么久需要 DOM API 和 BOM API.
这主要指在浏览器端运行的 JS. 如果是运行在服务端的 JS , 则需要使用 node.js 的 API, 就不太需要关注 DOM 和 BOM

重要概念: ECMAScript

这是一套 “标准”, 无论是啥样的 JS 引擎都要遵守这个标准来实现.

  • 啥叫标准? 车同轨, 书同文. 秦始皇最大的贡献之一, 就是制定了一套标准. 三流公司做产品, 一流公司做标准.

JavaScript的三种书写模式

行内式

直接嵌入到 html 元素内部

<input type="button" value="点我一下" onclick="alert('haha')">
  • 注意, JS 中字符串常量可以使用单引号表示, 也可以 使用双引号表示.
  • HTML 中推荐使用双引号, JS 中推荐使用单引号.

内嵌式

写到 script 标签中

<script>
	alert("haha");
</script>
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>HTML嵌入JavaScript的第二种方式</title>
</head>
<body>
    <input type="button" value="我是一个。。"/>
    <input type="button" value="我是一个按钮对象"/>
     <script type="text/javascript">
        window.alert("hello world!");
    </script>
</body>
</html>
  • 一般放在body的最后面

外部式

写到单独的 .js 文件中

<script type="text/javascript" src="hello.js"></script>
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>HTML中嵌入JavaScript的第三种方式</title>
</head>
<body>
<script type="text/javascript" src="file/JS1.js"></script>
</body>
</html>
  • 注意, 这种情况下 script 标签中间不能写代码. 必须空着(写了代码也不会执行).
  • 适合代码多的情况.

JavaScript的输出输出方式

输入: prompt

// 弹出一个输入框
prompt("请输入您的姓名:");

在这里插入图片描述

输出: alert

 <script>
        // 弹出一个输出框
        alert("hello");
</script>

弹出一个警示对话框, 输出结果

在这里插入图片描述

输出: console.log

在控制台打印一个日志(供程序员看)

// 向控制台输出日志
console.log("这是一条日志");

注意: 在 VSCode 中直接输入 “log” 再按 tab 键, 就可以快速输入 console.log
在这里插入图片描述

重要概念:
console 是一个 js 中的 “对象”
. 表示取对象中的某个属性或者方法. 可以直观理解成 “的”
console.log 就可以理解成: 使用 “控制台” 对象 “的” log 方法.

JavaScript的一些基础语法

虽然我们的JS跟我们的Java没有必然的联系,但是在代码编写的时候,有很多相似的地方,我们只需要了解一些JS跟Java的不同的地方

变量的使用

创建变量(变量定义/变量声明/变量初始化)

var name = 'zhangsan';
var age = 20;
  • var 是 JS 中的关键字, 表示这是一个变量.
  • = 在 JS 中表示 “赋值”, 相当于把数据放到内存的盒子中. = 两侧建议有一个空格
  • 每个语句最后带有一个 ; 结尾. JS 中可以省略 ; 但是建议还是加上.
  • 注意, 此处的 ; 为英文分号. JS 中所有的标点都是英文标点.
  • 初始化的值如果是字符串, 那么就要使用单引号或者双引号引起来.

我们的JavaScript和Java不一样的是,JS是弱类型语言,简单来说就是变量没有类型,常量值有类型

使用例子

var name = prompt("请输入姓名:");
var age = prompt("请输入年龄:");
var score = prompt("请输入分数");
alert("您的姓名是: " + name + "\n" + "您的年龄是: " + age + "\n" + "您的分数是: " +
score + "\n");  
  • +表示字符串拼接, 也就是把两个字符串首尾相接变成一个字符串.
  • \n 表示换行
  • JavaScript 中还支持使用 let 定义变量. 用法和 var 基本类似. 用法上的差异此处暂时不讨论.

如何理解JS的动态类型(弱类型)

JS 的变量类型是程序运行过程中才确定的(运行到 = 语句才会确定类型)

var a = 10; // 数字
var b = "hehe"; // 字符串

随着程序运行, 变量的类型可能会发生改变.

var a = 10; // 数字
a = "hehe"; // 字符串

这一点和 C Java 这种静态类型语言差异较大.
C, C++, Java, Go 等语言是静态类型语言. 一个变量在创建的时候类型就确定了, 不能在运行时发生改变.如果尝试改变, 就会直接编译报错

  • JavaScript是一种弱类型语言,没有编译阶段,一个变量可以随意给其赋值。什么类型的都可以。
  • 变量没有手动赋值时,默认赋值为:undefined。未声明变量使用会报错。

局部变量和全局变量

  • 类似C语言:
  • 全局变量在函数体之外声明。浏览器关闭的时候才会销毁。
  • 局部变量:在函数体内部声明。在函数体执行完后才销毁。
  • 当一个变量声明的时候没有使用var关键字,那么不管这个变量是在哪里声明的,都是全局变量。

基本数据类型

JS 中内置的几种类型

  • number: 数字. 不区分整数和小数.
  • boolean: true 真, false 假.
  • string: 字符串类型.
  • undefined: 只有唯一的值 undefined. 表示未定义的值.
  • null: 只有唯一的值 null. 表示空值.

number 数字类型

JS 中不区分整数和浮点数, 统一都使用 “数字类型” 来表示. 0,-1,123,…小数,复数,

var a = 1;
var a = 07; // 八进制整数, 以 0 开头
var b = 0xa; // 十六进制整数, 以 0x 开头
var c = 0b10; // 二进制整数, 以 0b 开头
  • 一个八进制数字对应三个二进制数字
  • 一个十六进制数字对应四个二进制数字. (两个十六进制数字就是一个字节)

特殊的数字值

  • Infinity: 无穷大, 大于任何数字. 表示数字已经超过了 JS 能表示的范围.

  • -Infinity: 负无穷大, 小于任何数字. 表示数字已经超过了 JS 能表示的范围.

  • NaN,表示Not a Number不是一个数字,但是属于Number类型。

var max = Number.MAX_VALUE;
// 得到 Infinity
console.log(max * 2);
// 得到 -Infinity
console.log(-max * 2);
// 得到 NaN
console.log('hehe' - 10);

注意:

  1. 负无穷大 和 无穷小 不是一回事. 无穷小指无限趋近与 0, 值为 1 / Infinity
  2. ‘hehe’ + 10 得到的不是 NaN, 而是 ‘hehe10’, 会把数字隐式转成字符串, 再进行字符串拼接.
  3. 可以使用 isNaN 函数判定是不是一个非数字

string字符串

基本规则
字符串字面值需要使用引号引起来, 单引号双引号均可

var a = "haha";
var b = 'hehe';
var c = hehe; // 运行出错

当字符串本身存在引号

var msg = "My name is "zhangsan""; // 出错
var msg = "My name is \"zhangsan\""; // 正确, 使用转义字符. \" 来表示字符串内部的引号.
var msg = "My name is 'zhangsan'"; // 正确, 搭配使用单双引号
var msg = 'My name is "zhangsan"'; // 正确, 搭配使用单双引号  

一些转义字符
有些字符不方便直接输入, 于是要通过一些特殊方式来表示.

  • \n
  • \
  • "
  • \t

创建字符串对象的方式

  • 第一种:var s=“sag”;(小String,属于String类型)
  • 第二种:var a2= new String(“ab”);(大String,属于Object类型)

boolean

在boolean类型中有一个Boolean()函数,会将非boolean类型,转换成boolean类型。

  • 当某个地方一定是boolean类型时,会自动转换成boolean类型。例如if后面的括号。
  • NaN,0,“”,null,undefined会自动转换成false.
console.log(true + 1);
console.log(false + 1)
  • 这样的操作其实是不科学的. 实际开发中不应该这么写.

undefined 未定义数据类型

如果一个变量没有被初始化过, 结果就是 undefined, 是 undefined 类型

var a;
console.log(a)

undefined 和字符串进行相加, 结果进行字符串拼接

console.log(a + "10"); // undefined10

undefined 和数字进行相加, 结果为 NaN

console.log(a + 10);

null 空值类型

null 表示当前的变量是一个 “空值”.

var b = null;
console.log(b + 10); // 10
console.log(b + "10"); // null10

注意:

  • null 和 undefined 都表示取值非法的情况, 但是侧重点不同.
  • null 表示当前的值为空. (相当于有一个空的盒子)
  • undefined 表示当前的变量未定义. (相当于连盒子都没有)

关于相等的细节

  • undefined == null 得到true

  • undefined === null 得到false

  • NaN 不等于任何数据,包括它自己

  • NaN == NaN 永远都是false

  • 那么如何判断是否为NaN?isNaN(数据)如果是NaN得到true 否则得到false

JS中的=的比较

  • ==是自带类型转换的比较
  • ===是不带自带类型的比较
0=="0"//true
0==="0"//false
  • 0==“0”,因为两个要比较的数据类型不等,所以先对其中一个做类型提升(这里把0->“0”)
  • 0===“0” 不做类型提升。两个比较的类型不同,所以结果就是false
  • 一般建议使用===和!==去做比较,不会出现一些内在逻辑错误

其他的运算符和条件判断符的用法跟Java是差不多的

数组

创建数组

使用 new 关键字创建

// Array 的 A 要大写
var arr = new Array();

使用字面量方式创建 [常用]

var arr = [];
var arr2 = [1, 2, 'haha', false]; // 数组中保存的内容称为 "元素"
  • 数据列表可以写任意个数据,如果多个数据用逗号隔开
  • 数组跟变量一样,数组中的元素也是无类型的((本质是一个引用类型)),所有数组可以保存任意的类型的元素,数组中放数组也可以

注意: JS 的数组不要求元素是相同类型.
这一点和 C, C++, Java 等静态类型的语言差别很大. 但是 Python, PHP 等动态类型语言也是如此.

获取数组元素

使用下标的方式访问数组元素(从 0 开始)

var arr = ['小猪佩奇', '小猪乔治', '小羊苏西'];
console.log(arr);
console.log(arr[0]);
console.log(arr[1]);
console.log(arr[2]);
arr[2] = '小猫凯迪';
console.log(arr);

如果下标超出范围读取元素, 则结果为 undefined

console.log(arr[3]); // undefined
console.log(arr[-1]); // undefined
  • 非法下标不会报错,但是会显示如果是读取值会获得undefined,如果是修改操作,那么会产生空洞数据

注意: 不要给数组名直接赋值, 此时数组中的所有元素都没了.

var arr = ['小猪佩奇', '小猪乔治', '小羊苏西'];
arr = '小猫凯迪';

新增数组元素

通过修改 length 新增

相当于在末尾新增元素. 新增的元素默认值为 undefined

var arr = [9, 5, 2, 7];
arr.length = 6;
console.log(arr);
console.log(arr[4], arr[5]);

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xl96MR4N-1670257665700)(JavaScript基础.assets/image-20221205192828555.png)]
通过下标新增

如果下标超出范围赋值元素, 则会给指定位置插入新元素

var arr = [];
arr[2] = 10;
console.log(arr)
  • 此时这个数组的 [0] 和 [1] 都是 undefined

使用push()新增

  • 在数组末尾添加元素
  • 也可以一次性添加多个,用逗号隔开
  • 返回值是新长度
var arr = [9, 5, 2, 7, 3, 6, 8];
var newArr = [];
for (var i = 0; i < arr.length; i++) {
	if (arr[i] % 2 != 0) {
		newArr.push(arr[i]);
	}
}
console.log(newArr);

unshift()

  • 在数组第一个位置添加元素
  • 也可以一次性添加多个,用逗号隔开
  • 返回值是新长度

删除数组中的元素

使用 splice 方法删除元素

var arr = [9, 5, 2, 7];
// 第一个参数表示从下表为 2 的位置开始删除. 第二个参数表示要删除的元素个数是 1 个
arr.splice(2, 1);
console.log(arr);
// 结果
[9, 5, 7]

使用pop()方法删除元素

  • 删除数组末尾的元素(一次只能删一个)
  • 返回值就是被删除的元素

使用shift()方法删除元素

  • 删除数组的第一个元素
  • 返回值是被删除的元素

函数

语法格式

// 创建函数/函数声明/函数定义
function 函数名(形参列表) {
	函数体
return 返回值;
} 
// 函数调用
函数名(实参列表) // 不考虑返回值
返回值 = 函数名(实参列表) // 考虑返回值
  • 函数定义并不会执行函数体内容, 必须要调用才会执行. 调用几次就会执行几次
function hello() {
	console.log("hello");
} 
// 如果不调用函数, 则没有执行打印语句
hello();
  • 调用函数的时候进入函数内部执行, 函数结束时回到调用位置继续执行. 可以借助调试器来观察.
  • 函数的定义和调用的先后顺序没有要求. (这一点和变量不同, 变量必须先定义再使用)

关于参数个数

实参和形参之间的个数可以不匹配. 但是实际开发一般要求形参和实参个数要匹配

function sum(var x,var y) {
	return x+y;
} 

如果实参个数比形参个数多, 则多出的参数不参与函数运算

sum(10, 20, 30); // 30

如果实参个数比形参个数少, 则此时多出来的形参值为 undefined

sum(10); // NaN, 相当于 num2 为 undefined

函数表达式

另外一种函数的定义方式

  • 有参数的函数function 函数名 ( 参数列表) { 函数体 },参数列表,就是定义需要几个数据,多个之间用逗号隔开,不需要写参数的类型
  • 如果用这种方式声明的函数,不能再它声明之前调用
var add = function() {
	var sum = 0;
	for (var i = 0; i < arguments.length; i++) {
		sum += arguments[i];
	}
	return sum;
} 
console.log(add(10, 20)); // 30
console.log(add(1, 2, 3, 4)); // 10
console.log(typeof add); // function
  • 有返回值的函数 语法: function 函数名 ( 参数列表) { 函数体 return 数据 },不需要写返回值的类型,可以返回变量值,也可以直接返回数据,函数内也可以不写return,只不过这个时候函数的返回值就是undefined

作用域

某个标识符名字在代码中的有效范围.
在 ES6 标准之前, 作用域主要分成两个

  • 全局作用域: 在整个 script 标签中, 或者单独的 js 文件中生效.
  • 局部作用域/函数作用域: 在函数内部生效.
// 全局变量
var num = 10;
console.log(num);
function test() {
	// 局部变量
	var num = 20;
	console.log(num);
}
function test2() {
	// 局部变量
	var num = 30;
	console.log(num);
}
test();
test2();
console.log(num);
// 执行结果
10
20
30
10

创建变量时如果不写 var, 则得到一个全局变量.

function test() {
	num = 100;
} 
test();
console.log(num);
// 执行结果
100

作用域链

  • 函数可以定义在函数内部
  • 内层函数可以访问外层函数的局部变量.
  • 内部函数可以访问外部函数的变量. 采取的是链式查找的方式. 从内到外依次进行查找.
var num = 1;
function test1() {
	var num = 10;
	function test2() {
		var num = 20;
		console.log(num);
	} 
}
test2(); 
test1();
// 执行结果
20

执行 console.log(num) 的时候, 会现在 test2 的局部作用域中查找 num. 如果没找到, 则继续去 test1 中查找. 如果还没找到, 就去全局作用域查找

在这里插入图片描述

对象

基本概念

  • 对象是指一个具体的事物. “电脑” 不是对象, 而是一个泛指的类别. 而 “我的联想笔记本” 就是一个对象.

在 JS 中, 字符串, 数值, 数组, 函数都是对象.

每个对象中包含若干的属性和方法.

  • 属性: 事物的特征.
  • 方法: 事物的行为.

JavaScript 的对象 和 Java 的对象概念上基本一致. 只是具体的语法表项形式差别较大.

定义对象的方法

使用 字面量 创建对象

var a = {}; // 创建了一个空的对象
var student = {
	name: '蔡徐坤',
	height: 175,
	weight: 170,
	sayHello: function() {
		console.log("hello");
	}
};
  • 使用 { } 创建对象
  • 属性和方法使用键值对的形式来组织.
  • 键值对之间使用 , 分割. 最后一个属性后面的 , 可有可无
  • 键和值之间使用 : 分割.
  • 方法的值是一个匿名函数.

使用对象的方法和属性

// 1. 使用 . 成员访问运算符来访问属性 `.` 可以理解成 "的"
console.log(student.name);
// 2. 使用 [ ] 访问属性, 此时属性需要加上引号
console.log(student['height']);
// 3. 调用方法, 别忘记加上 ()
student.sayHello();  
//增加一个属性hello
student.hello = 175;

使用 new Object 创建对象

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(); 
  • 注意, 使用 { } 创建的对象也可以随时使用 student.name = “蔡徐坤”; 这样的方式来新增属性.

使用 构造函数 创建对象

基本语法

前面的创建对象方式只能创建一个对象. 而使用构造函数可以很方便 的创建 多个对象

如果想创建多个对象此时写起来就比较麻烦. 使用构造函数可以把相同的属性和方法的创建提取出来, 简化开发过程

function 构造函数名(形参) {
	this.属性 =;
	this.方法 = function...
}
var obj = new 构造函数名(实参);

注意:

  • 在构造函数内部使用 this 关键字来表示当前正在构建的对象.
  • 构造函数的函数名首字母一般是大写的.
  • 构造函数的函数名可以是名词.
  • 构造函数不需要 return
  • 创建对象的时候必须使用 new 关键字.

例子

function Cat(name, type, sound) {
	this.name = name;
    this.type = type;
	this.miao = function () {
		console.log(sound); // 别忘了作用域的链式访问规则
	}
}
} 
var mimi = new Cat('咪咪', '中华田园喵', '喵');
var xiaohei = new Cat('小黑', '波斯喵', '猫呜');
var ciqiu = new Cat('刺球', '金渐层', '咕噜噜');
console.log(mimi);
mimi.miao();

理解 new 关键字
new 的执行过程:

  • 先在内存中创建一个空的对象 { }
  • this 指向刚才的空对象(将上一步的对象作为 this 的上下文)
  • 执行构造函数的代码, 给对象创建属性和方法
  • 返回这个对象 (构造函数本身不需要 return, 由 new 代劳了)

JavaScript 对象不区分 “属性” 和 “方法”

JavaScript 中的函数是 “一等公民”, 和普通的变量一样. 存储了函数的变量能够通过 ( ) 来进行调用执行

JavaScript 对象没有 private / public 等访问控制机制.

对象中的属性都可以被外界随意访问.

JavaScript 没有 “类” 的概念

对象其实就是 “属性” + “方法” .
类相当于把一些具有共性的对象的属性和方法单独提取了出来, 相当于一个 “月饼模子”
在 JavaScript 中的 “构造函数” 也能起到类似的效果.
而且即使不是用构造函数, 也可以随时的通过 { } 的方式指定出一些对象
在 ES6 中也引入了 class 关键字, 就能按照类似于 Java 的方式创建类和对象了.

JavaScript 对象没有 “继承”

继承本质就是 “让两个对象建立关联”. 或者说是让一个对象能够重用另一个对象的属性/方法.
JavaScript 中使用 “原型” 机制实现类似的效果.

JavaScript 没有 “多态”

多态的本质在于 “程序猿不必关注具体的类型, 就能使用其中的某个方法”.
C++ / Java 等静态类型的语言对于类型的约束和校验比较严格. 因此通过 子类继承父类, 并重写父类的方法的方式 来实现多态的效果.
但是在 JavaScript 中本身就支持动态类型, 程序猿在使用对象的某个方法的时候本身也不需要对对象的类型做出明确区分. 因此并不需要在语法层面上支持多态.

WebAPI

什么是 WebAPI

前面学习的 JS 分成三个大的部分

  • ECMAScript: 基础语法部分
  • DOM API: 操作页面结构
  • BOM API: 操作浏览器

WebAPI 就包含了 DOM + BOM.

这个是 W3C 组织规定的. (和制定 ECMAScript 标准的大佬们不是一伙人).

前面学的 JS 基础语法主要学的是 ECMAScript, 这让我们建立基本的编程思维. 相当于练武需要先扎马步.但是真正来写一个更加复杂的有交互式的页面, 还需要 WebAPI 的支持. 相当于各种招式.

DOM 基本概念

什么是 DOM

DOM 全称为 Document Object Model.
W3C 标准给我们提供了一系列的函数, 让我们可以操作:

  • 网页内容
  • 网页结构
  • 网页样式

DOM 树

一个页面的结构是一个树形结构, 称为 DOM 树.

<html>
    <head>
        <title>文档标题</title>
    </head>
    <body>
        <a href="">我的链接</a>
        <h1>我的标题</h1>
    </body>
</html>

在这里插入图片描述

重要概念:

  • 文档: 一个页面就是一个 文档, 使用 document 表示.
  • 元素: 页面中所有的标签都称为 元素. 使用 element 表示.
  • 节点: 网页中所有的内容都可以称为 节点(标签节点, 注释节点, 文本节点, 属性节点等). 使用 node表示.

这些文档等概念在 JS 代码中就对应一个个的对象.所以才叫 "文档对象模型" .

获取元素

也就是找到页面(文档)中对应的一个标签

前面的几种方式获取元素的时候都比较麻烦. 而使用 querySelector 能够完全复用前面学过的 CSS 选择器知识, 达到更快捷更精准的方式获取到元素对象

querySelector

var element = document.querySelector(selectors);
  • selectors 包含一个或多个要匹配的选择器的 DOM字符串 DOMString 。 该字符串必须是有效的
  • CSS选择器字符串;如果不是,则引发 SYNTAX_ERR 异常
  • 表示文档中与指定的一组CSS选择器匹配的第一个元素的 html元素 Element 对象.
    • 如果您需要与指定选择器匹配的所有元素的列表,则应该使用 querySelectorAll()
  • 可以在任何元素上调用,不仅仅是 document。 调用这个方法的元素将作为本次查找的根元素
  • 如果返回值是null,说明不存在我们要选择的元素

例子

<div class="box">abc</div>
<div id="id">def</div>
<h3><span><input type="text"></span></h3>
<script>
    //找到第一个class为box的元素
	var elem1 = document.querySelector('.box');
	console.log(elem1);
	//找到id为id的元素
	var elem2 = document.querySelector('#id');
	console.log(elem2);
	//找到第一个 h3标签下 span 标签下的input元素
	var elem3 = document.querySelector('h3 span input');
	console.log(elem3);
</script>

querySelectorAll
使用 querySelectorAll 用法和上面类似

<div class="box">abc</div>
<div id="id">def</div>
<script>
	//选中所有标签为div的元素
	var elems = document.querySelectorAll('div');
	console.log(elems);
</script>

事件初识

基本概念

JS 要构建动态页面, 就需要感知到用户的行为.

  • 用户对于页面的一些操作(点击, 选择, 修改等) 操作都会在浏览器中产生一个个事件, 被 JS 获取到, 从而进行更复杂的交互操作

事件三要素

  • 事件源: 哪个元素触发的
  • 事件类型: 是点击, 选中, 还是修改?
  • 事件处理程序: 进一步如何处理. 往往是一个回调函数.
<button id="btn">点我一下</button>
<script>
	var btn = document.querySelector('#btn');
	btn.onclick = function () {
		alert("hello world");
	}
</script>
  • 我们的btn就是事件源——对应一个元素
  • 我们点击这个按钮的点击就是对应的事件类型
  • function 这个匿名函数就是事件处理程序
    • 其中 btn.onclick = function() 这个操作称为 注册事件/绑定事件

这个匿名函数相当于一个回调函数, 这个函数不需要程序猿主动来调用, 而是交给浏览器, 由浏览器自动在合适的时机(触发点击操作时) 进行调用.

操作元素

我们操作元素和操作结点其最终的目的也就是改变我们的DOM树,从而让我们在浏览器能看到页面的变化

获取/修改元素内容

innerText
Element.innerText 属性表示一个节点及其后代的“渲染” 文本内容

// 读操作
var renderedText = HTMLElement.innerText;
// 写操作
HTMLElement.innerText = string;
<div>
	<span>hello world</span>
	<span>hello world</span>
</div>

<script>
	var div = document.querySelector('div');
	// 读取 div 内部内容
	console.log(div.innerText);
	// 修改 div 内部内容, 界面上就会同步修改
	div.innerText = 'hello js <span>hello js</span>';
</script>

在这里插入图片描述

  • 可以看到, 通过 innerText 无法获取到 div 内部的 html 结构, 只能得到文本内容.
  • 修改页面的时候也会把 span 标签当成文本进行设置

innerHTML

Element.innerHTML 属性设置或获取HTML语法表示的元素的后代.

// 读操作
var content = element.innerHTML;
// 写操作
element.innerHTML = htmlString;
<div>
	<span>hello world</span>
	<span>hello world</span>
</div>
<script>
	var div = document.querySelector('div');
	// 读取页面内容
	console.log(div.innerHTML);
	// 修改页面内容
	div.innerHTML = '<span style="font-size:60px;font-weight:bolder;color:yellow;">hello js</span>'
</script>

在这里插入图片描述

可以看到 innerHTML 不光能获取到页面的 html 结构, 同时也能修改结构. 并且获取到的内容保留的空格和换行

关于innerHTML如何实现DOM结构的改变
在这里插入图片描述

获取/修改元素属性

可以通过 Element 对象的属性来直接修改, 就能影响到页面显示效果

<img src="rose.jpg" alt="这是一朵花" title="玫瑰花">
<script>
	var img = document.querySelector('img');
	console.dir(img);//打印这个元素的所有属性
</script>

在这里插入图片描述

<img src="rose.jpg" alt="这是一朵花" title="玫瑰花">
<script>
	var img = document.querySelector('img');
	// console.dir(img);
	console.log(img.src);
	console.log(img.title);
	console.log(img.alt);
</script>

在这里插入图片描述

实例

<img src="rose.jpg" alt="这是一朵花" title="玫瑰花">
<script>
	var img = document.querySelector('img');
	img.onclick = function () {
		if (img.src.lastIndexOf('rose.jpg') !== -1) {
			img.src = './rose2.png';
		} else {
			img.src = './rose.jpg';
		}
}
</script>

此时点击图片就可以切换图片显示状态. (需要提前把两个图片准备好)

获取/修改表单元素属性

表单(主要是指 input 标签)的以下属性都可以通过 DOM 来修改

  • value: input 的值.
  • disabled: 禁用
  • checked: 复选框会使用
  • selected: 下拉框会使用
  • type: input 的类型(文本, 密码, 按钮, 文件等)

代码示例: 切换按钮的文本.

<input type="button" value="播放">
<script>
	var btn = document.querySelector('input');
	btn.onclick = function () {
		if (btn.value === '播放') {
			btn.value = '暂停';
		} else {
			btn.value = '播放';
		}
	}
</script>
<input type="text" id="text" value="0">
<input type="button" id="btn" value='点我+1'>
<script>
var text = document.querySelector('#text');
var btn = document.querySelector('#btn');
//input 具有一个重要的属性 value, 这个 value 决定了表单元素的内容
btn.onclick = function () {
	var num = parseInt(text.value);
	console.log(num);
	num++;
	text.value = num;
}
</script>

如果是输入框, value 表示输入框的内容, 修改这个值会影响到界面显式; 在界面上修改这个值也会影响到代码中的属性
如果是按钮, value 表示按钮的内容. 可以通过这个来实现按钮中文本的替换

获取/修改样式属性

行内样式操作

CSS 中指定给元素的属性, 都可以通过 JS 来修改

element.style.[属性名] = [属性值];
element.style.cssText = [属性名+属性值];  

“行内样式”, 通过 style 直接在标签上指定的样式. 优先级很高. 适用于改的样式少的情况

style 中的属性都是使用 驼峰命名 的方式和 CSS 属性对应的.
例如: font-size => fontSize, background-color => backgroundColor 等
这种方式修改只影响到特定样式, 其他内联样式的值不变.

<div style="font-size: 20px; font-weight: 700;">
哈哈
</div>
<script>
	var div = document.querySelector('div');
	div.onclick = function () {
		var curFontSize = parseInt(this.style.fontSize);
		curFontSize += 10;
		this.style.fontSize = curFontSize + "px";
	}
</script>
  • 这样就实现了点击一下字体就变大的效果

类名样式操作

element.className = [CSS 类名];

修改元素的 CSS 类名. 适用于要修改的样式很多的情况

操作节点

新增节点

分成两个步骤

  • 创建元素节点
  • 把元素节点插入到 dom 树中.
    • 第一步相当于生了个娃, 第二步相当于给娃上户口.
<div class="container">
</div>
<script>
	var div = document.createElement('div');
	div.id = 'mydiv';
	div.className = 'box';
	div.innerHTML = 'hehe';
	console.log(div);
</script>

此时发现, 虽然创建出新的 div 了, 但是 div 并没有显示在页面上. 这是因为新创建的节点并没有加入到DOM 树中

插入节点到 DOM树中

element.appendChild(aChild)  
<div class="container">
</div>
<script>
	var div = document.createElement('div');
	div.id = 'mydiv';
	div.className = 'box';
	div.innerHTML = 'hehe';
	var container = document.querySelector('.container');
	container.appendChild(div);
</script>

删除节点

使用 removeChild 删除子节点

oldChild = element.removeChild(child);
  • child 为待删除节点
  • element 为 child 的父节点
  • 返回值为该被删除节点
  • 被删除节点只是从 dom 树被删除了, 但是仍然在内存中, 可以随时加入到 dom 树的其他位置.
  • 如果上例中的 child节点 不是 element 节点的子节点,则该方法会抛出异常.

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/64948.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

SSM整合:mybatis层-P17

首先构建新的项目。 MYSQL&#xff1a; 在mysql中创建我们需要的表 CREATE DATABASE ssmbuild;USE ssmbuild;DROP TABLE IF EXISTS books;CREATE TABLE books ( bookID INT(10) NOT NULL AUTO_INCREMENT COMMENT 书id, bookName VARCHAR(100) NOT NULL COMMENT 书名, bookCo…

【深入浅出Spring原理及实战】「IOC容器初始化」彻底让你明白和理解运行原理和源码流程

前言介绍 本篇文章篇幅较大&#xff0c;希望读者可以慢慢阅读&#xff0c;建议收藏&#xff0c;分多次阅读学习。 学习源码的过程当中&#xff0c;有几点建议&#xff1a; 一定要学会抓重点&#xff0c;归纳核心类、核心方法、核心步骤&#xff1b; 分析源码我们不需要太过于纠…

MongoDB 存储引擎

简单回顾 上次我们说到了关于 mongodb 的集群&#xff0c;分为主从集群和分片集群&#xff0c;对于分片集群中的分片这里需要注意如下几点&#xff0c;一起来回顾一下&#xff1a; 对于热点数据某些分片键&#xff08;分片键是集合中每个文档中存在的索引字段或复合索引字段&a…

qt历史数据管理模块(模块化程序)功能块复制直接使用不冲突

一、前言 qt对历史数据管理部分个人总结的模块化程序&#xff0c;直接按照步骤复制粘贴程序&#xff0c;直接实现历史数据管理功能&#xff0c;无需花费脑筋在理清各个思路&#xff0c;适合快速编写组装程序 二、环境 windows qt5.7 sqlite3 三、正文 建议参照前文&…

【uni-app】uni-app之云开发uniCloud跨全栈开发笔记总结,包括一个 schema自动生成代码小案例(附详细截图)

1- 前言 本文主要讲解如何使用uni-app 和 uniCloud 云开发&#xff0c;实现小案例&#xff0c;不需要后端&#xff0c;来实现全栈开发。 2- 概念 2.1 什么是uni-app uni-app 是一个使用Vue.js开发所有前端应用的框架&#xff0c;开发者编写一套代码&#xff0c;可发布到iOS、…

对信息系统生命周期各阶段进行风险评估的要点汇总

概述 风险评估应贯穿于评估对象生命周期 各阶段中。评估对象生命周期各阶段中涉及的风险评估原则和方法昆一致的&#xff0c;但由干各阶段实施内容对象、安全需求不同.使得风险评估的对象、目的、要求等各方面也有所不同。在规划设计阶段&#xff0c;通过风险评估以确定评估对…

pytorch笔记(九)转置卷积、膨胀卷积

Transposed Convolution (转置卷积) 别名:Fractionally Strided Convolution (小数步长的卷积)、Deconvolution(逆/反卷积) 作用:upsampling(上采样) 模拟: PS:不是恢复原始值(因为一般情况下矩阵不可逆,无法等式左右两边同乘矩阵的逆得到原始矩阵) 转置卷积的…

为什么分布式系统这么火?

做Java的升职空间有限&#xff0c;可以说如果不想一辈子做程序员&#xff0c;只能往其他方向进行拓展&#xff0c;比如做到产品经理之类的或者技术总监。 可如果还是想做和技术相关的职业&#xff0c;那么架构师是很好的一步。 可是要如何做一名优秀的架构师呢&#xff1f; …

每天五分钟机器学习:经典的机器学习PCA的核心——特征分解技术

本节重点 本节我们将学习特征分解,特征分解是矩阵分析中非常重要的概念,它也可以应用到PCA算法中,本节先讲解什么是特征分解,然后讲解特征分解在PCA算法中的应用。 数学知识准备 如上所示是方差的定义,方差是度量一组数据的分散程度 如上所示是方差的定义,协方差是…

BSP板机支持包、linux启动分析、ARM裸机编程

文章目录一、BSP二、驱动驱动的基本要素三、启动分析1.uboot2.uboot的作用3.uboot相关命令关键的内容&#xff1a;1&#xff09;bootargs&#xff0c;启动参数2&#xff09;启动命令3&#xff09;修改启动延时时间4&#xff09;复位开发板5&#xff09;修改本地IP地址6&#xf…

Matlab群体智能优化算法之大鲹鱼优化算法(GTO)

Giant Trevally Optimizer : A Novel Metaheuristic Algorithm for Global Optimization and Challenging 一、灵感来源二、算法的初始化三、GTO的数学模型  Phase1&#xff1a;广泛搜索  Phase2&#xff1a;选择区域  Phase3&#xff1a;攻击四、流程图五、伪代码六、实…

[附源码]计算机毕业设计四川景区管理系统Springboot程序

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

SWT Table列自适应大小

要实现列自适应大小首先需要保证Table根据窗口拖动而改变大小。 Window中提供setShellStyle可以设置外壳样式。 构造一个新的自定义器对话框&#xff0c;在构造函数中添加setShellStyle(getShellStyle() | SWT.RESIZE);即可改变自定义对话框大小&#xff0c;如&#xff1a; ge…

[附源码]Python计算机毕业设计SSM教师教学质量评价系统(程序+LW)

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

数据卷(Data Volumes)dockerfile

目录一、宿主机与容器之间的文件拷贝1、利用MySQL镜像安装MySQL服务2、从容器中拷贝文件到宿主机3、从宿主机拷贝文件到容器二、数据卷三、数据卷容器四、Dockerfile1、自定义centos&#xff0c;具备vim及ifconfig作用2、自定义tomcat8一、宿主机与容器之间的文件拷贝 1、利用…

Linux虚拟化网络之vlan配置

问题描述&#xff1a; Linux主机划分两个vlan&#xff0c;服务器server1的物理网卡的IP地址为1.1.1.1/24&#xff0c;服务器server2的物理网卡的IP地址为1.1.1.2/24。物理网卡下要虚拟化出来两个Vlan子接口&#xff0c;vlan10中主机的IP地址分别为10.10.10.1/24和10.10.10.2/2…

99%的人都把三层架构和SpringMVC的关系搞错了

99%的人都把三层架构和SpringMVC的关系搞错了&#xff01;&#xff01;&#xff01; 先说结论&#xff0c; 三层架构和SpringMVC的关系就是没有关系。 很多人之前把SpringMVC中的M-Model当作三层架构中的servicedao&#xff08;包括我&#xff09;&#xff0c;这个是一个错误…

前端知识粉碎机

diff算法 Dep的作用是收集观察者以及当数据发生变动时通知观察者去更新。 Dep.notify()通知观察者去更新。 当数据改变时&#xff0c;就会触发setter&#xff0c;然后触发Dep.notify&#xff0c;通知订阅者&#xff0c;比对新旧虚拟节点&#xff0c;判断是否是同类标签&#xf…

Emlog博客文章图片自动加水印插件

内容目录一、详细介绍二、效果展示1.部分代码2.效果图展示三、学习资料下载一、详细介绍 给Emlog博客的上传图片添加水印可以有效地保护作品版权&#xff0c;有效地打击那些转载文件不留原作者地址的垃圾网站&#xff0c;部分Emlog博主通常都是手动给图片添加水印&#xff0c;…

MySQL学习记录(7)SQL优化

3. SQL优化 3.1、插入数据 3.1.1 insert 如果我们需要一次性往数据库表中插入多条记录&#xff0c;可以从以下三个方面进行优化 insert into tb_test values(1,tom); insert into tb_test values(2,cat); insert into tb_test values(3,jerry); .....&#xff08;1&#xf…