变量
作用: 用来保存值
保存两种类型的值: 基本类型值,和引用类型值;
访问方式: 按值访问 和 按引用访问
操作方式:
直接操作保存在变量中的实际的值。
引用类型的值是保存在内存中的对象,不能直接操作对象的内存空间。实际上是在操作对象的引用而不是实际的对象。
数据类型 两大类 8 种数据类型
最新的 ECMAScript 标准定义了 8 种数据类型: 参考 MDN javascript 数据类型和数据结构
七种原始类型 – 简单数据类型
Boolean
Null Null 类型只有一个值就是null值
Undefined Undefined类型只有一个值就是undefined值
Number
BigInt
String
Symbol
和 Object – 复杂数据类型 ( ECMAScript 定义的对象中有两种属性:数据属性和访问器属性 来自 MDN)
原始值的定义
除 Object 以外的所有类型都是不可变的(值本身无法被改变)。例如: JavaScript中字符串是不可变的
(译注:如: JavaScript 中对字符串的操作一定返回了一个新字符串,原始字符串并没有被改变)。
我们称这些类型的值为“原始值”。
Javascript 操作符:
一元操作符 只能操作一个值的操作符是一元操作符。!(非) ++a --b
++前置和++后置共同点 所有编程语言都是一样的
前者是自增在返回值; 后者是先返回值,再自增。
let a = 10;
// console.log(a++) 10
let b = 10;
// console.log(++b) 11
正确解释:
n++ 将变量 n 的当前值加 1, n-- 则将 n 的值减 1。
错误示范:
console.log(4++); 数值4是一个数值常量没法自增。
算数操作符
加 减 乘 除 取余
减乘除操作符应用于操作数时遵循的规则:
1: 有一个操作数为 NaN,结果就是 NaN
2: 如果有一个操作数不是数值,则调用后台的 Number()方法转化为数值,再进行操作。
+操作符有些特殊
遇到+操作符,不会调用后台的 Number()方法。
1: 如果有一个操作数是 NaN,那么结果就是 NaN
2: 数值相加字符相连。
比较操作符
关系操作符应用于操作数遵循的规则。
1: 如果都是数值,则直接进行比较。
2: 如果一个是数值,则另外一个调用后台 Number()转化为数值,再比
3: 如果都是字符串时,比字符串对应的字符编码值
str.charCodeAt(index) 表示给定索引处的 UTF-16 代码单元(代码单元可能包括多个码点)
4: 如果是布尔值,调用后台的 Number()转化数值
相等操作符
相等操作符: 比较之前,会转换类型
全等操作符: 而全等不会转换类型。
对于基本数据类型: == 是数值的比较
对于引用数据类型: == 是地址值的比较
相等操作符应用一操作数遵循的规则
1: 如果有一个操作数是布尔值则会转化为数值。
2: 如果有一个操作数是字符串则会转化为对应的编码值。
3: 如果有一个操作数是布尔值,则在比较相等性之前先将其转换为数值——false 转换为 0,而true 转换为 1
特殊列子
3: null 值 或者 undefined 值与其他操作数比较相等时,比较之前不会将值转化为任何值。
所以 null == flase 返回 false
注意:
ECMA 规定
null == undefined 返回 true
null === undefined 返回false
NAN == NAN 返回false
null == 0 返回false
undefined == 0 返回false
undefined和null的区别
undefined——表示变量声明过但并未赋过值。它是所有未赋值变量默认值,例如:
var a; // a 自动被赋值为 undefined
null——表示一个变量将来可能指向一个对象。一般用于主动释放指向对象的引用,例如:
var temp = [‘a’,‘b’];
temp = null; // 释放指向数组的引用 垃圾回收机制回收
比较运算符号总结: 由于相等和不相等操作符存在类型转换问题,而为了保持代码中数据类型的完整性,我们推荐使用全等和不全等操作符。
逗号操作符
逗号操作符 在一条语句中执行多个操作。
let a = 10, b = 20 ; 分号结束语句。
let a, b , c, d ; 同时声明四个变量
逻辑操作符
逻辑或
1: 遇见 true 时就返回。
2: 操作符左边的操作值返回 false,那么直接返回右边的操作值(不管右边的值是真还是假)。
var a = false || 6; // 6
var b = 3 || (0 && 2); // 3
var c = 0 || (2 && 3); // 3
逻辑与
var a = 5 && 6;
console.log(a); //返回的结果为 6
1: 操作符左边返回 true,那么直接返回右边的操作值(不管右边的值是真还是假)
2: 遇见 false 直接返回 false 操作值
注意: 布尔型转换问题
在 C 语言和 javascript 中 对于数值型 非零为真,零为假。 而在 java 中则不可以。
typeof 操作符
作用: typeof 操作符返回一个字符串,表示未经计算的操作数的类型 (都是小写的字符串。 object function )
在 ES 规范中 函数是一种对象,并不是一种数据类型。
但是因为函数有一些特殊的属性,所以也可以使用 typeof 操作符来区分函数和对象。
确定一个值是哪种基本类型可以使用 typeof 操作符,
确定一个值是哪种引用类型可以使用 instanceof 操作符。
instanceof 运算符用于检测构造函数的 prototype 属性是否出现在某个实例对象的原型链上。
语法
typeof 运算符后接操作数
typeof operand
参数
operand
一个表示对象或原始值的表达式,其类型将被返回。
只有 null 这个 object 返回的是 false, 其它 object 都返回的是 true
操作符优先级别
分组()
一元运算符
算数运算符
比较运算符
相等运算符
逻辑运算符
分支语句和循环语句
if 语句
do-while 语句
whild 语句
for 语句
for-in 语句
break 和 continue 语句
switch 语句
基本字符串和字符串对象的区别
字符串字面量 (通过单引号或双引号定义) 和 (没有通过 new 生成字符串对象实例)的字符串都是基本字符串。
JavaScript 会自动将基本字符串转换为字符串对象,只有将基本字符串转化为字符串对象之后才可以使用字符串对象的方法。
JavaScript 会自动将基本字符串转化为字符串对象并且调用相应的方法或者执行查询。
注意: 字符串的不可变性 一经创建都不可变化。
javascript使用字符串的方法操作字符串时,都不会修改原来的字符串,而是在内存堆中又创建一个新的字符串。
注意点一: 基本数据类型的变量赋值; (具体到值的传递)
var num = 10;
var num1 = num; // 把 10 复制一份放到新开辟的内存空间; num1 指向新空间;
基本数据类型中 字符串的不可变性(特殊:)
var num = 10;
num = 20; // 直接在原有的栈内存空间中替换值为20;
var str = “andy”; // 开辟内存空间,存储"andy" str 指向内存空间;
str = “李白”; // 又会开辟一个新的内存空间,存储新的字符串"李白" str 指向新空间;
注意点二: 引用数据类型的变量赋值; (地址的复制)
var obj = {name: ‘zs’, age: 30} ; // 栈内存中是地址值,而堆内存中是对象; obj 指向栈内存空间地址值;
var newobj = obj; //新开辟一个空间,把 obj 空间的地址值,复制一份放到新开辟的空间中,newobj 指向空间;
基本包装类型: Number String Boolean
String 类型用于表示由零或多个 16 位 Unicode 字符组成的字符序列,即字符串。字符串可以由双
引号(")或单引号(’)表示
作用: 方便操作基本类型值。
每当读取一个基本类型值得时候,后台就会创建一个对应的基本类型的包装对象,从而让我们调用一些方法来操作这些数据。
为什么我们可以
var str = ‘some’
var newste = str.split(" “);
实际上底层
var str = new String(‘some’);
var newstr = str.split(” ");
str = null 释放引用;
直接通过 new String() new Number() new boolean()构造函数显示创建包装对象;
字符集: Unicode 编码&解码
JavaScript程序使用的是Unicode字符集编写的。例如: 我们在js代码中写的字符"a" 只是显示形式,
真正底层的是字符"a"的码点,使用unicode编码之后的形式,\u0061。
HTML实体字符串(16进制)
<!--应用在HTML中示例-->
<div>编码解码</div>
中国
HTML实体字符串(10进制)
<!--应用在HTML中示例-->
<div>编码解码</div>
中国
16进制Unicode编码(可以同时用于HTML与JS中)
<!--应用在HTML中示例-->
<div>\u7F16\u7801\u89E3\u7801</div>
<script>
// 应用在JavaScript中示例
alert('\u7F16\u7801\u89E3\u7801');
</script>
function tounicode(data) {
if (data == '') return '请输入汉字'
var str = ''
for (var i = 0; i < data.length; i++) {
str += '\\u' + parseInt(data[i].charCodeAt(0), 10).toString(16)
}
return str
}
function tohanzi(data) {
if (data == '') return '请输入十六进制unicode'
data = data.split('\\u')
var str = ''
for (var i = 0; i < data.length; i++) {
str += String.fromCharCode(parseInt(data[i], 16).toString(10))
}
return str
}
Java中对字符串的解释
// let str = 'string' // console.log(str.substring(0, 10))
// 字符串的不可变性 // 例如: "hello字符串" 永远就是 hello unicode的字符序列。
// 不可变性质有一个优点: 编译器可以让字符串共享。
// equals方法: equalsIgnoreCase 字符串比较方法 不忽略大小写 忽略大小写
// 判断字符串的想等性 如果虚拟机始终将相同的字符串共享, 就可以使用 = 运算符检测是否相等。
// 但实际上只有字符串常量是共享的, 而 + 或 substring 等操作产生的结果并不是共享的。
//理解Java字符串
//3.3.4 Unicode 和 char 类型章节: 在 Java 中,char 类型描述了 UTF-16 编码中的一个代码单元。
//3.6 字符串章节说: 从概念上讲, Java 字符串就是 Unicode 字符序列。
//3.6.6 码点与代码单元章节说: Java 字符串由 char 值序列组成。
//总结: char 数据类型是一个采用 UTF-16 编码表示 Unicode 码点的代码单元。
// 大多数的常用 Unicode 字符使用一个代 码单元就可以表示,而辅助字符需要一对代码单元表示。
函数
1: ECMAScript 中的所有参数传递的都是值,不可能通过引用传递参数。
2: 没有被实参赋值的形参会自动赋值为 undefined 值:
3: js 中没有没有重载的概念。不过我们可以定义一个函数接受不同的参数来模拟重载。
4: 函数的属性 每个函数都包含两个属性 length 和 prototype。
深入理解值传递和引用传递
当两个变量共享一个对象的内存地址时,此时修改一个变量中的引用就会改变另外一个对象。此时就可以理解为引用传递。
当两个变量共享同一个内存地址,当又创建一个新对象赋值给共享其他对象的内存地址时,会切断与上一个对象的联系
变量的内存地址指向新对象,但不会影响原来变量的指向(就可以解释上面说的函数的参数传递是值传递)
let obj = { name: ‘zs’ , age: 30 }
let obj1 = obj; 保存的是同一个内存地址
obj1.name = ‘修改了值’ 此时把 obj 内存空间里面的值修改了;
obj1 = { } 又创建一个新对象赋值给 obj1,切断与原来的指向,
obj1.name = ‘li’ 这里做的操作不会影响 obj 对象。
打印 obj { name: '修改了值 ', age: 30 }
打印 obj1 { name: ‘li’ }
深入理解 1: Js代码被执行发生了什么
从执行环境 作用域 变量对象 函数角度分析
疑问回答:
从全局环境分析: 当代码一执行,就会构建全局执行环境的作用域,同时创建一个包含全局变量对象的作用域链(实际上作用域链并不会包含变量对象,只是 变量对象的引用列表。)。
从函数角度分析: 函数创建的时候,会预先创建一个包含变量对象的作用域链,保存在函数的 _scoped属性里函数调用的时候复制 函数的_scoped 属性,构建执行环境的作用域链。
let arr = [1, 2, 3]
let arr1 = [1, 2, 3, 4, 5, 6]
let a = 10
function fun(name, age, gender) {
console.log(name)
console.log(age)
console.log(gender)
}
fun('张三', 30, '男')
console.dir(fun)
ƒ fun(name, age, gender)
arguments: null
caller: null
length: 3
name: "fun"
prototype: {constructor: ƒ} 每个函数都有一个 prototype 属性
__proto__: ƒ ()
[[FunctionLocation]]: bowons.html:20
[[Scopes]]: Scopes[2] 该属性包含变量对象的引用列表。
0: Script {arr: Array(3), arr1: Array(6), a: 10} script标签里面的变量
1: Global {parent: Window, postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, …} window对象
来源:CSDN
作者:行之所致
链接:https://blog.csdn.net/weixin_44811301/article/details/104060603