文章目录
一. JavaScript 的两种引入方法
1. 内部引入和外部引入
2.引入的两个位置
<head>
<meta charset="utf-8" />
<title></title>
<!-- 引入的两个位置 -->
<script type="text/javascript">
alert("it is my world")
</script>
</head>
<body>
<!-- 引入的两个位置:body 标签的底部 -->
<script src="js/001.js">
</script>
</body>
3. 引入位置不同引起的变化
二. 基本数据类型和基本语法
1.浏览器控制台
console.log() // 在控制台打印内容
2.变量声明
var声明一切
3.流程控制
if(){
}else if(){
}
else{
}
4.数据类型
-
Number类型
js 不区分小数和整数(不区分int 和float),统一为number类型
console.log(1/3===(1-2/3)) // return false 避免使用浮点数进行计算 -
字符串
不区分单引号和双引号
PHP中区分单引号和双引号,双引号可以识别变量。
-
布尔值
true 和 false
-
比较运算符
- NaN:not a number 用来说明非数字
NaN 不等于一切 包括自身
- NaN:not a number 用来说明非数字
console.log(NaN == 1); //false
console.log(NaN == NaN); //false
console.log(NaN == "hello world"); //false
isNaN() 用来判断NaN
== 和 ===
== 会先进行隐式强制类型转换再进行比较
=== 不允许进行强制类型转换,要求类型和值一致才为true
true == 1 return true; true === 1 return false ;
-
null 和 unidefined
null 表示为空,
unidefined 表示为未定义
-
数组
-
定义:
var a = [1,2,3]var b = new Array(1,2,3) -
超出下标范围为unidefined
-
-
对象
定义:中括号定义数组,大括号定义对象,对象内部为键值对的形式
var people = { name : 'li', age : 90, weight : 100 }调用
console.log(people.name)
5.严格检查模式
use strict;
- 需要放在代码的开头
- 检查JavaScript随意性带来的一些问题
- 需要设置编辑器支持es6语法
- 局部变量尽量使用let定义
6、布尔值为false的情况
null,undefined,空字符串,数字0,空数组,空对象,负值在条件判断中被认为是false
字符串0 不会被认为是false
三.数据类型
1.字符串类型
-
单引号和双引号包裹的效果相同
-
字符串的可变性:不可变
可以使用下标访问,不能使用下标改变
可以对字符串再赋值
-
多行字符串
var str = ` hello world hello world ``` 定义多行字符串
-
模板字符串
在多行字符的基础上进行定义
var msg = `${str}` console.log(msg) -
获取字符串长度
str.length() -
常用字符串函数
str.substr(start[,length])根据给定的起始下标和长度截取字符串。
str.indexOf(subString[, startIndex])根据值搜索字符串,返回搜索到字符串的下标
stringObj.split([separator[, limit]])根据分界符将字符串分割为数组
str.toUpperCase() str.toLowerCase()
2.数组类型
- Array() 可以包含任意的数据类型
arr.length
- 获取长度
arr.indexOf()
- 查找成功,根据元素值返回索引
- 查找失败,返回-1
arr.slice(1,2)
- 截取数组元素
arr.push() arr.pop()
- 对栈尾部压入 删除并弹出元素
arr.unshift('a') arr.shift(2)
- 队列头部压入或者弹出元素
arr.join('-')
-
数组转换为字符串并设置元素间连接符
arr (4) [1, 2, 3, 4] arr.join('-') "1-2-3-4" -
数组转字符串
arr.join('')
var arr = ['hello',1,'world','nimade'];
console.log(arr.length);
console.log(arr.indexOf('world')); //2
console.log(arr[0].slice(1,2)); //e
arr.push('h');
console.log(arr); // [ "hello", 1, "world", "nimade", "h" ]
console.log(arr.pop()); // h
console.log(arr);// [ "hello", 1, "world", "nimade" ]
console.log(arr.unshift('e'));
var string = arr.join('*');
console.log(string); // e*hello*1*world*nimade
数组排序
arr.sort()
3.对象类型
对象的属性以键值对的形式呈现,访问一个不存在的属性并不会报错
JavaScript中的对象的键是字符串,值是对象
这里的对象并不是指面向对象
person['weight']; delete person.weight; 这两种访问模式是等价的
-
对象的声明
var person = { name: 'li', age: 50, msg: 'haha' } -
对象属性的添加
person.weight = '50' -
对象属性的删减
delete person.weight -
判断一个属性或方法是否在对象中
var $bool2 = 'age' in person;属性或方法如果是继承则 in 返回结果为 true
-
判断一个属性或方法是否只为该对象所拥有(不是继承过来的)
person.hasOwnProperty('toString') false -
使用一个不存在的属性:undefined
即使是在严格检查模式下,访问一个被删除或原本不存在的属性会返回undefined,不会报错。
4.流程控制
if(){
}else if(){
}else{
}
while(){
}
for(var i = 0; i!=100; i++){
}
for(var i in arr){
console.log(arr[i])
}
// i 遍历的是数组的索引
for(var i of arr){
console.log(i);
}
// i遍历的是数组的值
5.Map 和 Set
Map和Set都是es6中的新特性,需要编辑器和浏览器支持es6语法
Map:类似python的字典,Set:无序不重复的集合
Map中常用函数:get(),set(),delete(),has(),clear()
// Map 的定义 : Map 类似于python的字典
var map = new Map([['li',100],['han',80],['jun',70]]);
// 获取值
console.log(map.get('li'));
console.log(map.get('hhh'));
// 增加值
console.log(map.set('hahaha',666));
// 删除值
console.log(map.delete('hahaha'));
console.log(map.has('aaa'));
console.log(map.clear());
Set中常用函数:add delete has
// Set:无序不重复的集合
var set = new Set([1,11,1,3]);
set.add(2);
set.delete(1);
console.log(set.has(3));
6.Iterator 迭代
迭代数组
// for in
var arr = [1,2,3,4,5]
for(var x in arr){
console.log(x);
}
// for of
for(var x of arr){
console.log(x);
}
迭代map
var map = new Map([['li',100],['han',80],['jun',70]]);
for(var x of map){ // 迭代map的每一个单元,即一个数组
console.log(x);
}
for(var x of map){
console.log(x[0]); // 迭代数组中的元素
}
迭代set
var set = new Set([1,11,1,3]);
for(var x of set){
console.log(x);
}
四.函数
1.定义函数
函数的两种定义
// 正常的定义模式
function abs(a,...rest){
if(rest.length != 0){
throw '参数过多';
}else if(typeof a !== 'number'){
throw "参数类型错误";
}
if(a >= 0){
return a;
}else{
return -a;
}
}
// 类似java匿名函数的定义模式
var abs2 = function(a){
// 检错
if(arguments.length > 1){
throw '参数过多';
}else if(typeof arguments[0] !== 'number'){
throw '参数类型错误';
}
if(a>=0){
return a;
}else{
return -a;
}
}
参数问题与arguments
对于给定个数的函数,可以传入多于形参个数的实参也可以不传入参数,不报错。
js引入arguments 数组用来保存传入的所有参数,而数组的长度就是传入参数的个数
通过 arguments.length 的不同实现不同的函数行为,从而可以实现重载?
es6新特性:可变长参数rest
用来接收除了已经定义之外传入的多余参数,类型为数组,所以也可以获取长度
function rest(a, ...rest){
for(var x of rest){
console.log(x);
}
}
rest(1,2,3)
结果:2 3
类似Java的可变长参数
2.变量的作用域
全局作用域和局部作用域
<script type="text/javascript">
'use strict';
// 全局作用域和局部作用域
var x = 1, y = 1;
function xx(){
console.log(y);
var x = 2;
console.log(x);
}
</script>
全局作用域:在所有函数声明和大括号之外定义的变量,贯穿整个js文档,在所有地方都可以使用这个全局变量
局部作用域
- 函数作用域:函数内声明的变量只能在函数内被访问
- 块作用域:在一个大括号内用let和const声明的变量,只能在这个大括号内被访问
function rest(a,...rest) {
for(var x of arguments){
const a = 1;
console.log(x);
}
console.log(a);
for(let i = 0;i!=100;i++){
}
console.log(i); // i is not defined
for(var j = 0;j!=100;j++){
}
console.log(j); // 没有问题
}
作用域链和变量提升
每一个函数作为一个作用域,如果出现函数嵌套就会出现作用域链。
function a1(){
b();
var c = 1;
function b(){
var c = 2;
console.log(c); // 2
}
}
a1();
function a2(){
var c = 1;
b();
function b(){
// var c = 2;
console.log(c); // 1
}
}
a2();
内部函数访问外部函数变量时根据链式查找决定变量是否能被访问。
函数b在内未查找到c的声明便向外查找
function a2(){
b();
var c = 1;
function b(){
// var c = 2;
console.log(c); // undefined
}
}
函数a2存在提升变量作用域的行为,返回undefined
function xx2(){
var y = 1 + z; //Uncaught ReferenceError: z is not defined
console.log(y);
}
function xx3(){
var y = 1 + z;
var z = 3;
console.log(y); // NaN 并不会报错
}
结论:js默认提升变量的作用域,将变量的声明提到最前面,但不进行赋值
内部函数可以调用外部函数定义变量,外部函数不能调用内部函数定义的变量
内部函数和外部函数声明变量同名,内部变量屏蔽外部变量
规范
头部对所有需要使用的变量进行声明
全局对象
函数可被视为变量,所有的全局变量都绑定在windows对象下。
var zz = 1;
console.log(zz);
console.log(window.zz) // 效果相同
// 定义一个old_alert 和 alert 效果相同
var old_alert = alert;
// old_alert(3);
var alert = function(){
}
alert(); // 原本window 下的alert() 函数被重写了
// 他又回来了
var alert = old_alert;
// alert(4);
// 作用域链的问题:局部作用域找不到变量(函数)则向外查找全局作用域,找不到则报错
规范
为了解决在一个全局变量命名冲突的问题:所有的全局变量都默认绑定在window对象下,当引入多个js文件时难免会发生重名问题。
使用一个独立的命名空间以解决这个问题,事实上许多框架也是这么干的。
li.name = 'li';
console.log(li.name);
let 和 var
function let1(){
while(1){
var x = 1;
break;
}
console.log(x); // 1
while(1){
let y = 1;
break;
}
console.log(y); // 1
for(var i = 1;i!=10;++i){
}
console.log(i); // 没有报错
for(let j = 1;j!=10;++j){
}
console.log(j); //Uncaught ReferenceError: j is not defined
}
- 在while中效果相同
- var的定义变量超出for仍能使用,let定义的变量超出for不能使用
const
const:只读变量,不可修改
规范:常量字母大写表示
// const 关键字
const M = 100; // 只读变量
//m = 200; //Uncaught TypeError: Assignment to constant variable.
3.方法
方法的定义
在对象或类里面定义的函数我们就说它是一个方法。
var person = {
name : 'li',
age: function(){
var now = new Date();
console.log(this.name, now.getFullYear() - 2000);
} // 类中的函数我们就说它是一个方法
}
// 方法调用:person.age()
function get_age(){
var now = new Date();
console.log(this.name, now.getFullYear() - 2000);
} // 每一个函数都是一个function对象,this此时指向这个function对象
var person2 = {
name: 'han',
age: get_age
}
this 关键字
每一个函数都是一个function对象,this此时指向这个function对象
apply 关键字
get_age.apply(person2, []);
apply可以改变this指针的指向
- 第一个参数为this指针指向的对象
- 第二个参数为对 对象进行的赋值
五.常用对象
1.Date 对象
var now = new Date();
now.getFullYear();
now.getMonth();
now.getDate(); // 获取GMT标准实践
now.getDay(); // 获取星期
now.getHours();
now.getMinutes();
now.getSeconds();
// 以上信息可能被修改,且不同计算机的数据可能不同
now.getTime(); // 获取时间戳,自 1970.1.1 0:00:00 开始至今的毫秒数,全球统一
// to
now.toLocaleString(); // "2020/1/21 上午10:28:47"
2.JSON
what is json?
- 基于EMCAscript 的轻量级数据交换语言
- 层次结构
- 可以提高网络的效率
对象转换JSON,JSON 转换对象
// JSON
var person = {
name: 'li',
age: 40
}
// 对象转换为JSON
var a = JSON.stringify(person);
// JSON 转换为对象
var b = JSON.parse(a);
json 和对象的区别
对象的格式化
"{"name":"li","age":40}" // json
{name: "li", age: 40} // 对象
六.面向对象编程
1.面向原型继承
对象.__proto__ = 对象
- 相当于继承的一种写法,但是两者都是对象
- 已有属性和方法会覆盖和重写原型中的属性和方法,但是没有的会被继承
var person = {
name: 'li',
age: 17,
run: function(){
console.log(this.name + ' run..');
}
}
var tom = {
name: 'tom',
age: 18,
run: function(){
console.log('t' + ' run..');
}
}
tom.__proto__ = person;
2.class继承
class定义一个类:构造器 + 方法
class 关键字构建的类中属性的定义都在构造器中完成
class animal{
constructor(name) { // 类中的构造器,所有属性在构造器内定义
this.name = name;
}
hello(){
alert('I am ' + this.name);
}
} // 类
var lion = new animal('lion'); // 定义一个对象
class 继承
class cat extends animal{
constructor(name,age) {
super(name);
this.age = age;
}
get_age(){
alert(this.age);
}
}
// 定义对象
var cat1 = new cat('tom', 18);
原型链
原型链是一个环形链,最后归于object
本文深入探讨JavaScript的引入方式、基本数据类型、语法、流程控制、数据类型操作、函数定义与作用域、常用对象如Date和JSON,以及面向对象编程的概念。详细解析了字符串、数组、对象的特性和操作,Map和Set的使用,Iterator迭代,函数的定义与调用,作用域链,变量提升,以及Date对象和JSON的转换。

被折叠的 条评论
为什么被折叠?



