[前端|JAVA脚本第1篇]一文搞懂JAVA的基本语法
作者:小教学发布时间:2023-09-18分类:程序开发学习浏览:95
欢迎来到脚本的奇妙世界!作为前端开发的基石、脚本为网页增色不少,赋予了静态页面活力与交互性。如果你是一名前端小白,对编程一无所知,或者只是听说过脚本却从未涉足过,那么你来对了地方!本篇博客将带领你逐步进入脚本的大门,一步一步地探索这门语言的基本语法和应用。无论你是想为网页添加动态效果,或是构建一个全功能的WEB应用程序,学习都是你迈向成功的必经之路.准备好了吗?让我们一起踏上这段令人兴奋的学习旅程吧!
本文目录
- 1.变量
- 变量初始化
- 2.词法语法
- 区分大小写
- 代码示例:
- 注释
- 单行注释
- 多行注释
- 直接量
- 空直接量
- 布尔直接量
- 数值直接量
- 字符串直接量
- 对象直接量
- 数组直接量
- 标识符
- 关键字和保留字
- 保留字
- 关键字
- 未来保留字
- 预定义变量和函数
- 分号
- 3.数据类型
- 原始数据类型
- 空值
- 未定义值
- 布尔值
- 数字
- 进制数
- 浮点数
- 数字的范围
- 非数
- 字符串
- 符号
- 引用数据类型
- 类型检测
- 类型
- 实例数
- Object.prototype.toString
- 构造函数
- 数组检测
- 4.表达式
- 字面量
- 数组初始化表达式
- 逗号分隔
- 嵌套数组
- 可省略元素
- 索引赋值
- 对象初始化表达式
- 属性访问器
- 语法
- 示例
- 5.运算符
- 在……里面
- 语法
- 参数
- 示例
- 实例数
- 检测类型
- 类型
- 语法
- 参数
- 返回值
- 算术运算符
- 实践示例
- 实现指数运算符
- 更新表达式
- 示例
- 前自增
- 前自减
- 后自增
- 后自减
- 赋值运算符
- 比较运算符
- 关系运算符
- 等值运算符
- 抽象相等比较算法
- 引用数据类型间比较
- 条件运算符
- 逻辑运算符
- 逻辑与
- 逻辑或
- 逻辑非
- 6.语句
- 如果为语句
- 单层条件判断
- 多层条件判断
- 对于语句
- 语法
- 最佳实践
- 代码示例
- 从尾部向前循环
- 位数的整倍循环
- 涉及多个变量的循环
- 而语句
- 语法
- 参数
- 示例
- 代码示例
- 交换机语句
- 语法
- 参数
- 关键词
- 示例
- 继续语句
- 示例
- 打破语句
- 示例
- 尝试-抓住语句
- 接住
- 总结
1.变量
在编程语言中,变量用于存储数据值.
JavaScript使用关键字var
来定义变量,使用等号来为变量赋值.
变量初始化
- Var是一个JS关键字,用来声明变量(Variable变量的意思)。使用该关键字声明变量后,计算机会自动为变量分配内存空间.
- AGE是程序员定义的变量名,我们要通过变量名来访问内存中分配的空间.
//声明变量同时赋值为18
var age = 18;
//同时声明多个变量时,只需要写一个 var, 多个变量名之间使用英文逗号隔开。
var age = 18, address ='火影村',salary = 15000;
2.词法语法
ECMAScript源码文本会被从左到右扫描,并被转换为一系列的输入元素,包括标识符、控制符、行终止符、注释和空白符.
同样地、ECMASRIPT也定义了一些关键字、字面量以及行尾分号补全的规则.
区分大小写
脚本是区分大小写的语言,也就是说,关键字、变量、函数名和所有的标识符(标识符)都必须采取一致的大小写的形式。但是需要注意的是,html和css并不区分大小写(尽管xhtml区分大小写),也就是说如果我们在用javascript控制html属性的时候对html来说id和ID没区别,但是脚本有区别。
代码示例:
Abc、abc是五个不同的变量名.
var abc = 1;
var Abc = 2;
var aBc = 3;
var abC = 4;
var ABC = 5;
console.log(abc, Abc, aBc, abC, ABC); // 1 2 3 4 5
注释
脚本不会执行注释。
我们可以添加注释来对脚本进行解释,或者提高代码的可读性。
单行注释
单行注释以两个斜杠开头
快捷键:ctrl + /
// let a;
多行注释
多行注释又叫块级注释,以/*开头,以*/结尾
快捷键:shift + alt + a
/*
以下代码为
声明变量并
赋值
*/
let a;
a = 1;
块级注释/**/可以跨行书写,但不能嵌套,否则会报错.
// Error
/*
注释1
/*
注释1.1
*/
*/
块级注释/**/中的那些字符也可能出现在正则表达式字面量里,所以块级注释对于被注释的代码块来说是不安全的.
/*
var rm_a = /a*/.match(s);
*/
直接量
脚本数据直接量:直接量(文字),又名字面量、就是可以在程序中直接使用的数据.
主要有以下几种直接量:
空直接量
null;
布尔直接量
true;
false;
数值直接量
// 十进制
1234567890;
字符串直接量
'foo';
'bar';
对象直接量
var o = { a: 'foo', b: 'bar', c: 42 };
// ES6中的简略表示方法
var a = 'foo',
b = 'bar',
c = 42;
var o = { a, b, c };
// 不需要这样
var o = { a: a, b: b, c: c };
数组直接量
[1954, 1974, 1990, 2014];
标识符
标识符,就是指变量、函数、属性的名字,或者函数的参数.标识符可以是按照下列格式规则组合起来的一或多个字符.
- 第一个字符必须是一个
字母
、下划线(_)
、或一个美元符号($)
- 其他字符可以是
字母
、下划线
、美元符号
或数字
标识符中的字母也可以包含扩展的ASCII或UNICODE字母字符,但我们不推荐这样做。
按照惯例、ECMASRIPT标识符采用驼峰大小写格式,也就是第一个字母小写,剩下的每个单词的首字母大写.
const firstSecond = 123;
const myCar = 'Toyota';
const doSomethingImportant = function () {};
关键字和保留字
和其他任何编程语言一样、脚本保留了一些标识符为自己所用。这些保留字不能用做普通的标识符.由于好多参考书的误导,貌似保留字和关键字是分开的,其实并不是,关键字只是保留字的一部分.
保留字包括关键字、未来保留字、空字面量和布尔值字面量那就是。
保留字
- 关键字关键字
- 未来保留字未来保留字
- 空字面量NullWrital
- 布尔值字面量布尔文学
关键字
以下关键字ES6规范中已实现
break do instanceof typeof
case else new var
catch finally return void
continue for switch while
debugger function this with
default if throw delete
in try class extends
const export import
未来保留字
以上是ECMAScript6的保留字,但在ECMAScript3版本中的保留字并不一样,若希望代码能在基于ECMAScript3实现的解释器上运行的话,应该避免使用以下保留字作为标识符。
abstract boolean byte char
constdouble enum final float
goto implements int interfacelong
native package private protected
public short static super
throw transient volatile synchronized
预定义变量和函数
此外、脚本预定义了很多全局变量和函数,应该避免把它们的名字用做标识符名。
String Number Boolean Array
Date Function Math Object
RegExp Error EvalError JSON
Infinity NaN isNaN isFinite
undefined arguments parseInt parseFloat
eval decodeURI encodeURI decodeURIComponent
encodeURIComponent RangeError ReferenceError
TypeError URIError SyntaxError
分号
脚本使用分号;将语句分隔开,这对增强代码的可读性和整洁性是非常重要的。
有些地方可以省略分号,有些地方则不能省略分号.
两条语句用两行书写,第一个分号可以省略
a = 3;
b = 4;
两条语句用一行书写,第一个分号不能省略
a = 3;
b = 4;
但脚本并不是在所有换行处都填补分号,只有在缺少了分号无法正确解析代码时、JAVASCRIPT才会填补分号换句话说,如果当前语句和随后的非空格字符不能当成一个整体来解析的话、脚本就在当前语句行结束处填补分号。
代码示例:
var a;
a = 3;
console.log(a);
脚本将其解析为:
var a;
a = 3;
console.log(a);
3.数据类型
JavaScript是一种弱类型语言或者说动态语言那就是。这意味着你不用提前声明变量的类型,在程序运行过程中,类型会被自动确定.
这也意味着你可以使用同个相同名称的变量保存不同类型的数据:
var foo = 42;
// foo is a Number now
var foo = 'bar';
// foo is a String now
var foo = true;
// foo is a Boolean now
ECMAScript标准定义了原始数据类型和引用数据类型,共七种内置类型:
- 原始数据类型(基本类型):按值访问,可以操作保存在变量中实际的值.
- 空值(空)
- 未定义(未定义)
- 布尔值(布尔值)
- 数字(数字)
- 字符串(字符串)
- 符号(符号)
- 引用类型(复杂数据类型):引用类型的值是保存在内存中的对象.
- 对象(对象)
- 布尔对象(布尔值)
- 数字对象(编号)
- 字符串对象(字符串)
- 函数对象(函数)
- 数组对象(数组)
- 日期对象(日期)
- 正则对象(RegExp)
- 错误对象(错误)
- 对象(对象)
原始数据类型
空值
空值null
是一个字面量,它不像undefined
是全局对象的一个属性.
null
是表示缺少的标识,指示变量未指向任何对象.把null
作为尚未创建的对象,也许更好理解.
代码示例:
foo
不存在,它从来没有被定义过或者是初始化过.
foo;
> "ReferenceError: foo is not defined"
foo
现在已经是知存在的,但是它没有类型或者是值.
var foo = null;
foo;
> null
未定义值
未定义值undefined
是全局对象的一个属性.也就是说,它是全局作用域的一个变量.undefined
的最初值就是原始数据类型undefined
那就是。
var foo;
console.log(foo);
// undefined
布尔值
布尔类型表示一个逻辑实体,可以有两个值:true
和false
数字
进制数
- 十进制:脚本化中默认的进制数
- 八进制:第一位必须是0、然后是0-7的数字组成
- 十六进制:前两位必须是
0x
,然后是0-9及A-F(字母不区分大小写)
// 十进制
var num1 = 10;
// 八进制的56
var num2 = 070;
// 十进制,因为有数字超过了7,这里是79
var num3 = 079;
// 十六进制的31
var num4 = 0x1f;
浮点数
var num = 0.1 + 0.2;
var sum = '2.3' * 100;
console.log(num);
// 0.30000000000000000004
console.log(sum);
// 229.99999999999997
上面例子表达的就是脚本的浮点型数据在计算时容易丢失精度,这一点并不仅在Java存在,建议处理这方面问题使用专用的数字处理类,比如Java里的BigDecima类来处理。
数字的范围
脚本中数值的范围是有效位数的,基本上够我们使用,我们仅需要知道以下几个知识点:
Number.MIN_VALUE
或Number.NEGATIVE_INFINITY
:表示SCRIPT中的最小值Number.MAX_VALUE
或Number.POSITIVE_INFINITY
:表示SCRIPT中的最大值Infinity
:表示无穷大-Infinity
:表示无穷小
非数
NaN
(不是数字)的含义是本该返回数值的操作未返回数值,返回了NaN
就不会抛出异常影响语句流畅性.
NaN
属性的初始值就是NaN
,和Number.NaN
的值一样.
在现代浏览器中(ES5环境)、NaN
属性是一个不可配置(不可配置)、不可写(不可写)的属性。但在ES3中,这个属性的值是可以被更改的,但是也应该避免覆盖。
编码中很少直接使用到NaN
那就是。通常都是在计算失败时,作为Math
的某个方法的返回值出现的(例如:Math.sqrt(-1)
)或者尝试将一个字符串解析成数字但失败了的时候(例如:parseInt("blabla")
).
字符串
脚本的字符串类型用于表示文本数据。它是一组16位的无符号整数值的元素.在字符串中的每个元素占据了字符串的位置.第一个元素的索引为0、下一个是索引1、依此类推。字符串的长度是它的元素的数量.
'foo';
'bar';
'1234';
'one line \n another line';
"John's cat";
符号
符号(符号)是ECMAScript第6版新定义的。该类型的性质在于这个类型的值可以用来创建匿名的对象属性.该数据类型通常被用作一个对象属性的键值,当这个属性是用于类或对象类型的内部使用的时候.
var myPrivateMethod = Symbol();
this[myPrivateMethod] = function () {
// ...
};
引用数据类型
引用类型通常叫做类(班级)、也就是说,遇到引用值,所处理的就是对象.
在ECMA-262标准中根本没有出现类这个词,而是定义了对象定义、逻辑上等价于其他程序设计语言中的类.
对象是由new
运算符加上要实例化的对象的名字创建的.
例如,下面的代码创建对象对象的实例:
var o = new Object();
这种语法与JAVA语言的相似,不过当有不止一个参数时、ECMASCRIPT要求使用括号。
如果没有参数,如以下代码所示,括号可以省略:
var o = new Object();
尽管括号不是必需的,但是为了避免混乱,最好使用括号.
类型检测
类型检测的方法:
typeof
instanceof
Object.prototype.toString
constructor
类型
typeof
操作符返回一个字符串,表示未经计算的操作数的类型.
typeof undefined;
// "undefined"
typeof null;
// "object"
typeof 100;
// "number"
typeof NaN;
// "number"
typeof true;
// "boolean"
typeof 'foo';
// "string"
typeof function () {};
// "function"
typeof [1, 2];
// "object"
typeof new Object();
// "object"
typeof
操作符适合对基本类型(除)null
之外)及function
的检测使用,而对引用数据类型(如阵列)等不适合使用。
更详细信息请查阅类型的操作符。
实例数
instanceof
运算符用于检测一个对象在其原型链中是否存在一个构造函数的prototype
属性.
左操作数为对象,不是就返回false
,右操作数必须是函数对象或者函数构造器,不是就返回TypeError
异常.
obj instanceof constr;
function Person() {}
function Student() {}
Student.prototype = new Person();
Student.prototype.constructor = Student;
const ben = new Student();
ben instanceof Student;
// true
const one = new Person();
one instanceof Person;
// true
one instanceof Student;
// false
ben instanceof Person;
// true
任何一个构造函数都有一个prototype
对象属性,这个对象属性将用作new
实例化对象的原型对象.
📍instanceof
适合用于判断对象是否属于数组、Date和RegExp等内置对象。
📍不同窗口或iframe
之间的对象类型检测无法使用instanceof
检测.
更详细信息请查阅实例
Object.prototype.toString
可以通过toString()
来获取每个对象的类型.
为了每个对象都能通过Object.prototype.toString
来检测,需要以Function.prototype.call
或者Function.prototype.apply
的形式来调用,传递要检查的对象作为第一个参数.
Obejct.prototype.toString.call(undefined);
// "[object Undefined]"
Obejct.prototype.toString.call(null);
// "[object Null]"
Obejct.prototype.toString.call(true);
// "[object Boolean]"
Obejct.prototype.toString.call('');
/// "[object String]"
Obejct.prototype.toString.call(123);
// "[object Number]"
Obejct.prototype.toString.call([]);
// "[object Array]"
Obejct.prototype.toString.call({});
// "[object Object]"
💡使用Object.prototype.toString
方法能精准地判断出值的数据类型.
⚠️注意事项:
- 方法重写:
Object.prototype.toString
属于对象的原型方法,而数组或函数等类型作为对象的实例,都重写了toString
方法.因此,不同对象类型调用toString
方法时,调用的是重写后的toString
方法,而非Object
上原型toString
方法,所以采用xxx.toString()
不能得到其对象类型,只能将xxx
转换成字符串类型.
构造函数
任何对象都有constructor
属性,继承自原型对象,constructor
会指向构造这个对象的构造器或构造函数.
Student.prototype.constructor === Student;
// true
数组检测
ECMAScript5将Array.isArray()
正式引入脚本、该方法能准确检测一个变量是否为数组类型.
Array.isArray(variable);
4.表达式
字面量
字面量(文字),又名直接量,即程序中直接使用的数据值。
// Null 字面量
const n = null;
// Undefined 字面量
const u = undefined;
// Boolean 布尔值字面量
const b1 = true;
const b2 = false;
// Number 数值字面量
const num = 1;
const nan = NaN;
// String 字符串字面量
const hello = 'hello';
const world = 'world';
// Regexp 正则字面量
const reg = /pattern/;
// Template Literal 模版字面量
const temp = `hello, ${world}`
数组初始化表达式
数组初始化表达式是通过一对方括号和其内由逗号隔开的列表构成的.初始化的结果是一个新创建的数组.
逗号分隔
数组的元素是逗号分隔的表达式的值.
空数组:[]
内留空即表示该数组没有任何元素
拥有两个元素的数组:第一个是3、第二个是7。
[1 + 2, 3 + 4]
嵌套数组
数组初始化表达式中的元素初始化表达式也可以是数组的初始化表达式.也就是说,这些表达式是可以嵌套的.
var matrix = [[1, 2, 3],[4, 5, 6],[7, 8, 9]]
可省略元素
数组直接量中的列表逗号之间的元素可以省略,这时省略的空位会填充值不存在.
var sparseArray = [1, , , , 5]
// 相当于
// [1, empty x 3, 5]
数组直接量的元素列表结尾处可以留下单个逗号,这时并不会创建一个新的值为undefined
的值.
const arr = [1, 2, 3, ]
console.log(arr)
// [1, 2, 3]
索引赋值
通过数组索引赋值,只会给指定索引所在位置赋值,而其中未赋值的索引位置则表示为空empty
,而非定义为undefined
。
let arr = [0, 1]
arr[10] = 10
console.log(arr);
// [0, 1, empty x 8, 10]
console.log(arr.length);
// 11
ary.filter(x => x === undefined);
// []
对象初始化表达式
对象和数组初始化表达式实际上是一个新创建的对象和数组.这些初始化表达式有时称作对象直接量和数组直接量那就是。然而和布尔值直接量不同,它们实际上不是原始表达式,因为它们所包含的成员或者元素都是子表达式.
对象初始化表达式和数组初始化表达式非常相似,只是方括号被花括号代替,并且每个子表达式都包含一个属性名和一个冒号作为前缀.
// 一个拥有两个属性成员的对象
var p = {
x: 2.3,
y: -1.2,
};
// 一个空对象
var q = {};
// q 的属性成员和 p 的一样
q.x = 2.3;
q.y = -1.2;
对象直接量也可以嵌套.
var rectangle = {
upperLeft: { x: 2, y: 2 },
lowRight: { x: 4, y: 5 },
};
脚本求对象初始化表达式的值的时候,对象表达式也都会各自计算一次,并且它们不必包含常数值:它们可以是任意脚本表达式。
(同样,对喜爱那个直接量中的属性名称可以是字符串而不是标识符(这在那些只能使用保留字或一些非法标识符作为属性名的地方非常有用)
var side = 1;
var square = {
upperLeft: {
x: p.x,
y: p.y,
},
lowerRight: {
x: p.x + side,
y: p.y + side,
},
};
属性访问器
属性访问表达式运算得到一个对象属性或一个数组元素的值.
脚本为属性访问定义了两种语法。
语法
- 第一种写法是一个表达式后跟随一个句点和标识符.表达式指定对象,标识符则指定需要访问的属性的名称.
expression.identifiler
- 第二种写法是使用方括号,方括号内是另一个表达式(这种方法适用于对象和数组)。第二个表达式指定要访问的属性的名称或代表要访问数组元素的索引.
expression[expression]
不管使用哪种形式的属性访问器,在句点和左方括号之前的表达式总是会首先计算.
- 如果计算结果是
null
或undefined
,表达式会抛出一个类型错误异常,因为这两个值都不能包含任意属性 - 如果计算结果不是对象,JAVAJEL会将其转换为对象
- 如果对象表达式后跟随句点和标识符,则会查找由这个标识符指定的属性值,并将其作为整个表达式的值返回
- 如果对象表达式后跟随一对方括号,则会计算方括号内的表达式的值并将其转换为字符串
不论哪种情况,如果命名的属性不存在,那么整个属性访问表达式的值就是undefined
那就是。
示例
var a = {x: 1, y: {z: 3}};
// 一个示例对象
var b = [a, 4, [5, 6]];
// 一个包含这个对象的示例数组
console.log(a.x);
// 1
console.log(a.y.z);
// 3
console.log(a["x"]);
// 1
console.log(b[1]);
// 4
console.log(b[2]["1"]);
// 6
console.log(b[0].x);
// 1
5.运算符
在……里面
in
运算符用于判断属性是否存在于对象中.
语法
key in obj;
参数
参数 | 说明 |
---|---|
key | 一个字符串类型或者Symbol类型的属性名或者数组索引(非Symbol类型将会强制转为字符串)。 |
object | 检查(或其原型链)是否包含具有指定名称的属性的对象. |
示例
var cars = new Array('Toyota', 'Nissan', 'Mercedes', 'Buick', 'Porsche');
0 in cars;
// true
1 in cars;
// true
'PI' in Math;
// true
var myCar = { make: 'Honda', model: 'Accord', year: '1998' };
'make' in myCar;
'model' in myCar;
实例数
instanceof
运算符用于测试构造函数的prototype
属性是否出现在对象的原型链中的任何位置.
代码示例:
target instanceof constructor;
检测类型
instanceof
可以检测某个对象是否是另一个对象的实例那就是。
const Person = function () {};
const student = new Person();
console.log(student instanceof Person);
// true
instanceof
可以检测父类型.
function Person() {}
function Student() {}
const p = new Person();
// 继承原型
Student.prototype = p;
const s = new Student();
console.log(s instanceof Student);
// true
console.log(s instanceof Person);
// true
类型
typeof
操作符返回一个字符串,表示未经计算的操作数的类型.
语法
typeof operand;
参数
参数 | 说明 |
---|---|
perand | 是一个表达式,表示对象或原始值,其类型将被返回 |
返回值
下表总结了typeof
可能的返回值.
有关类型和原始值的更多信息,可查看脚本数据结构页面。
类型 | 结果 |
---|---|
未定义 | 'undefined' |
空值 | 'object' |
布尔型 | 'boolean' |
数 | 'number' |
细绳 | 'string' |
符号 | 'symbol' |
宿主对象 | 依赖于实施 |
函数对象 | 'function' |
任何其他对象 | 'object' |
算术运算符
算术运算符使用数值(字面量或者变量)作为操作数进行运算并返回一个数值.
标准的算术运算符就是加减乘除+
、-
、*
和/
那就是。
当操作数是浮点数时,这些运算符表现得跟它们在大多数编程语言中一样(特殊要注意的是,除零会产生Infinity
).
运算符 | 描述 | 示例 |
---|---|---|
+ | 加法 | 1 + 1 = 2 |
- | 减法 | 2 - 1 = 1 |
* | 乘法 | 3 * 3 = 9 |
/ | 除法 | 10 / 5 = 2 |
% | 求余,返回相除后余值 | 12 % 5 = 2 |
++ | 自增(更新运算符),分为前自增和后自增 | 具体参考更新运算符 |
-- | 自减(更新运算符),分为前自减和后自减 | 具体参考更新运算符 |
- | 一元负值符,返回操作数的负值 | -foo |
+ | 一元正值符,若操作数在操作前非数字类型,将试图将其转换成数字类型 | +foo |
** | 指数运算符,计算基(底数)的指数(指数)次方 | 2 ** 3 = 8 |
实践示例
console.log(-9 % 2);
// -1
console.log(1 + -+(+(+-+1)));
// 2
实现指数运算符
function calculateExponent(base, exponent) {
if (exponent === 1) {
return base;
} else {
return base * calculateExponent(base, exponent - 1);
}
}
更新表达式
更新表达式包括前自增/自减运算符和后自增/自减运算符那就是。
示例
前自增
前自增:先自增,再赋值
let n = 10;
// 前自增
const res = ++n;
console.log(n);
// 11
console.log(res);
// 11
前自减
前自减:先自减,再赋值
let n = 10;
// 前自减
const res = --n;
console.log(res);
// 9
console.log(n);
// 9
后自增
后自增:先赋值,再自增
let n = 10;
// 后自增
const res = n++;
console.log(res);
// 10
console.log(n);
// 11
后自减
后自减:先赋值,再自减
let n = 10;
// 后自减
const res = n--;
console.log(res);
// 10
console.log(n);
// 9
赋值运算符
一个赋值运算符(赋值运算符)将它右边操作数的值赋给它左边的操作数。
下列为ECMAScript标准规范的赋值运算符:
* = /= %= += -= <<= >>= >>>= &= ^= |= **=
运算名称 | 简写的操作符 | 分解含义 | 符号 |
---|---|---|---|
赋值 | x = y | x = y | = |
加法赋值 | x += y | x = x + y | += |
减法赋值 | x -= y | x = x - y | -= |
乘法赋值 | x *= y | x = x * y | *= |
除法赋值 | x /= y | x = x / y | /= |
求余赋值 | x %= y | x = x % y | %= |
求幂赋值 | x ** y | x = x ** y | ** |
左移位赋值 | x <<= y | x = x << y | <<= |
右移位赋值 | x >>= y | x = x >> y | >>= |
无符号右移位赋值 | x >>>= y | x = x >>> y | >>>= |
按位与赋值 | x & y | x = x & y | & |
按位异赋值 | x ^= y | x = x ^ y | ^= |
按位或赋值 | `X | =y` | `x=x |
比较运算符
比较运算符比较它的操作数并返回一个基于表达式是否为true
的逻辑值.
比较运算符分为关系运算符(关系运算符)**和**等值运算符(相等运算符)那就是。
- 操作数可以是数字,字符串,逻辑,对象值.
- 字符串比较是基于标准的字典顺序,使用unicode值。
- 在多数情况下,如果两个操作数不是相同的类型、脚本会尝试转换它们为恰当的类型来比较。这种行为通常发生在数字作为操作数的比较.
- 类型转换的例外是使用
===
和!==
操作符,它们会执行严格的相等和不相等比较.这些运算符不会在检查相等之前转换操作数的类型.下面的表格描述了该示例代码中的各比较运算符.
关系运算符
运算符 | 描述 | 返回true 的示例 |
---|---|---|
大于> | 左边的操作数大于右边的操作数返回true | b > a |
大于等于>= | 左边的操作数大于或等于右边的操作数返回true | b >= a a >= 1 |
小于< | 左边的操作数小于右边的操作数返回true | a < b 1 < 2 |
小于等于<= | 左边的操作数小于或等于右边的操作数返回true | a <= b b <= 5 |
等值运算符
运算符 | 描述 | 返回true 的示例 |
---|---|---|
等于== | 如果两边操作数相等时返回true | a == 1 '1' == 2 1 == '1' |
不等于!= | 如果两边操作数不相等时返回true | a != 2 b != '1' |
全等=== | 两边操作数相等且类型相同时返回true | a === 1 |
不全等!== | 两边操作数不相等或类型不同时返回true | a !== '1' 1 !== '1' |
抽象相等比较算法
- 若类型(X)与类型(Y)相同,则
- 若类型(X)为未定义,返回
true
- 若类型(X)为为空,返回
true
- 若类型(X)为编号,则
- 若x为NaN,返回
false
- 若y为nan,返回
false
- 若x与y为相等数值,返回
true
- 若x为+0且y为-0,返回
true
- 若x为-0且y为+0,返回
true
- 返回
false
- 若x为NaN,返回
- 若类型(X)为字符串
- 当x和y为完全相同的字符序列(长度相等且相同字符在相同位置)时返回
true
- 否则,返回
false
- 当x和y为完全相同的字符序列(长度相等且相同字符在相同位置)时返回
- 若类型(X)为布尔值
- 当x和y为同为
true
或者同为false
时返回true
- 否则,返回
false
- 当x和y为同为
- 当x和y为引用用一对象时返回
true
那就是。否则,返回false
那就是。
- 若类型(X)为未定义,返回
- 若x为空且y为未定义,返回
true
- 若x为未定义的且y为为空,返回
true
- 若类型(X)为数字且类型(Y)为字符串,返回比较
x == ToNumber(y)
的结果 - 若类型(X)为字符串且类型(Y)为编号,返回比较
ToNumber(x) == y
的结果 - 若类型(X)为布尔值,返回比较
ToNumber(x) == y
的结果 - 若类型(Y)为布尔值,返回比较
x == ToNumber(y)
的结果 - 若类型(X)为字符串或编号,且类型(Y)为对象,返回比较
x == ToPrimitive(y)
的结果 - 若类型(X)为对象且类型(Y)为字符串或编号,返回比较
ToPrimitive(x) == y
的结果 - 返回
false
按以上相等之定义:
- 字符串比较可以按这种方式强制执行:
'' + a == '' + b
- 数值比较可以按这种方式强制执行:
+a == +b
- 布尔值比较可以按这种方式强制执行:
!a == !b
等值比较操作保证以下不变:
A !== B
等价于!(A == B)
A == B
等价于B == A
、除了A与B的执行顺序.
相等运算符不总是传递的.例如,两个不同的字符串对象,都表示相同的字符串值;==
运算符认为每个String
对象都与字符串值相等,但是两个字符串对象互不相等.
new String('a') == 'a'
和'a' == new String('a')
皆为true
new String('a') == new String('a')
为false
字符串比较使用的方式是简单地检测字符编码单元序列是否相同.不会做更复杂的、基于语义的字符或者字符串相等的定义以及UNICODE规范中定义的排序顺序。所以unicode标准中认为相等的字符串值可能被检测为不等。实际上这一算法认为两个字符串已经是经过规范化的形式.
引用数据类型间比较
const a = function() {};
const b = function() {};
console.log(a === b);
// false
console.log([] === []);
// false
console.log({} === {});
// false
当我们访问引用数据类型(对象、数组、函数等等)的值时,首先从栈中获得该对象的地址指针,然后再从堆内存中取得所需的数据.
变量a
实际保存的是指向堆内存中对象的一个指针,而变量b
保存的是指向堆内存中的另一个对象的指针,虽然这两个对象的值时一样的,但它们是独立的两个对象,占了两份内存空间,所以它们互不相等.
而当将一个为引用数据类型的值的变量赋值给另一个变量时,即拷贝了前者的内存空间的地址指针,因此它们都指向堆内存中同一个对象.
let x = {}
let y = x
console.log(x === y)
// true
条件运算符
**条件运算符(条件运算符)*是脚本中唯一的一个*三元运算符(三个操作数),有时直接称做三元运算符.
variable = boolean_expression ? true_value : false_value;
本质上,这就是基于对boolean_expression
求值的结果,决定给变量variable
赋什么值.如果求值结果是true
,则给变量variable
赋值true_value
;如果求值结果是false
,则给变量variable
赋值false_value
那就是。
逻辑运算符
逻辑运算符常用于对操作数进行布尔运算,经常和关系运算符一样配合使用.逻辑运算符将多个关系表达式组合起来组成一个更复杂的表达式.逻辑运算符分为逻辑与&&
、逻辑或||
、逻辑非!
三种.
逻辑与
逻辑与运算符由两个和号&&
表示,有两个操作数,只有在两个操作数都为true
时,结果才返回true
,否则返回false
那就是。
逻辑与的真值表
第一个操作数 | 第二个操作数 | 结果 |
---|---|---|
true | true | true |
true | false | false |
false | true | false |
false | false | false |
逻辑或
逻辑与运算符由两个和号&&
表示,有两个操作数,只有在两个操作数都为true
时,结果才返回true
,否则返回false
那就是。
逻辑与的真值表
第一个操作数 | 第二个操作数 | 结果 |
---|---|---|
true | true | true |
true | false | false |
false | true | false |
false | false | false |
逻辑非
逻辑非操作符由一个叹号(!
表示,可以应用于ECMASRIPT中的任何值.无论这个值是什么数据类型,这个操作符都会返回一个布尔值.逻辑非操作符首先会将它的操作数转换成一个布尔值,然后再对其求反.
console.log(!null);
// t null
console.log(!undefined);
// t NaN
console.log(!0);
// t 数值0
console.log(!NaN);
// t NaN
console.log(!'');
// t 空字符串
console.log(!'123');
// f 非空字符串
console.log(!Infinity);
// f 任意非0数值(包括Infinity)
console.log(!{ a: 1 });
// f 对象
6.语句
如果为语句
条件语句用于基于不同的条件来执行不同的动作.
在脚本中,我们可使用以下条件语句:
- 如果为语句--只有当指定条件为
true
时,使用该语句来执行代码 - 如果为…Else语句--当条件为
true
时执行代码,当条件为false
时执行其他代码 - 如果为…否则如果为…Else语句--使用该语句来选择多个代码块之一来执行
- 交换机语句--使用该语句来选择多个代码块之一来执行
当一个逻辑条件为真,用if
语句执行一个语句.当这个条件为假,使用可选择的else
从句来执行这个语句.
单层条件判断
if (condition) {
statement_1;
}
[else {
statement_2;
}] //推荐使用严格的语句块模式,语句else可选
参数 | 说明 |
---|---|
condition | 为任何返回结果(若非boolean 类型会被ECMAScrpt转换)为true 或false 的表达式.如果条件式为true ,statement1 会被执行;否则statement2 会被执行 |
statement1(2) | 为任意语句(代码块),甚至可以将另一个if 语句嵌套七种 |
多层条件判断
if (condition_1) {
statement_1;
} [else if (condition_2) {
statement_2;
}]
...
[else if (condition_n_1) {
statement_n_1;
}] [else {
statement_n;
}]
要执行多个语句,可以使用语句块({…})来分组这些语句。
对于语句
对于语句也是一种前测试循环语句,但它具有在执行循环之前初始化变量和定义循环后要执行的代码的能力.
语法
for (initialization; expression; post - loop - expression) {
// statement
}
参数:
initialization
初始化表达式:表达式通常会初始化一个或多个循环计数器(变量),但语法上是允许一个任意复杂度的表达式,通常为一条声明赋值语句(只在循环开始之前执行一次)。expression
循环条件判断:执行循环语句前的判断语句(通常为比较表达式),若为true
则执行循环语句,否则则不执行循环语句,并跳出循环语句.post-loop-expression
计数器变量更新:循环执行语句执行后执行的计数器变量更新表达式,更新循环计数器(变量),以进入下一次循环条件判断.statement
循环执行语句:当循环条件满足时所执行的语句,执行完毕后执行计数器变量更新语句(利用break
、continue
语句除外)。
最佳实践
代码示例
var count = 10;
for (let i = 0; i < count; i++) {
console.log(i);
}
从尾部向前循环
位数的整倍循环
// 五位数的数字
const num = 99999;
for (let i = 1; i < num; i *= 10) {
// 被除数 num
// 除数
const divisor = i * 10;
// 整除部分
const divided = Math.floor(num / divisor);
// 余数
const remainder = num % divisor;
console.log(i, divisor);
// i divisor
// 1. 1 10
// 2. 10 100
// 3. 100 1000
// 4. 1000 10000
// 5. 10000 100000
}
涉及多个变量的循环
for (let i = 0, j = 10; i < 10; i++, j--) {
sum += i * j;
}
若在循环中一次迭代改变多个变量,则必须使用到逗号运算符,它将初始化表达式和自增表达式合并入一个表达式中以用于for
循环.
而语句
而语句可以在某个条件表达式为真的前提下,循环执行指定的一段代码,直到那个表达式不为true
时结束循环.
语法
while (expression) statement;
参数
参数 | 描述 |
---|---|
expression | 条件表达式,在每次循环前被求值.如果求值为true ,statement 就会被执行.如果求值为false ,则跳出while 循环执行后面的语句. |
statement | 只要条件表达式求值为true 、该语句就会一直被执行.要在循环中执行多条语句,可以使用块语句({ ... } )包住多条语句. |
注意:使用break
语句在expression
计算结果为真之前停止循环.
示例
代码示例
var i = 0;
while (i < 10) {
i += 2;
}
var cars = ['BMW', 'Volvo', 'Saab', 'Ford'];
var text = '';
var i = 0;
while (i < cars.length) {
text += cars[i] + '<br>';
i++;
}
交换机语句
switch
语句允许一个程序求一个表达式的值并且尝试去匹配表达式的值到一个case
标签.如果匹配成功,这个程序执行相关的语句.
语法
switch (expression) {
case value_1:
statements_1
[break;]
case value_2:
statements_2
[break;]
...
default:
statements_def
[break;]
}
工作原理:首先设置表达式expression
(通常是一个变量)。随后表达式的值会与结构中的每个case
的值做比较.如果存在匹配,则与该case
关联的代码块会被执行.请使用break
来阻止代码自动地向下一个case
运行.
参数
参数 | 说明 |
---|---|
expression | 用于比较的表达式 |
value_(n) | 与expression 比较的值 |
statement(n) | 执行语句 |
关键词
case
:表示一种情况,如果expression
等于value
,就执行statement
break
:会使代码跳出switch
语句,如果没有关键词break
,代码执行就会继续进入下一个case
那就是。default
:说明了表达式的结果不等于任何一种情况时的操作(事实上,它相对于Else从句)。
示例
var myCar = 'Porsche'
switch (myCar) {
case 'Nissan': alert("My car is Nissan");
break;
case 'Honda': alert("My car is Honda");
break;
case 'Porsche': alert("My car is Porsche");
break;
default: alert("I have no car");
}
继续语句
继续语句用于结束当前(或标签)的循环语句的本次迭代,并继续执行循环的下一次迭代。
示例
在for
语句中使用continue
var num = 0;
for (var i = 1; i < 10; i++) {
if (i % 5 == 0) {
continue;
}
num++;
}
console.log(num);
// 8
打破语句
打破语句用于立即退出最内层的循环或switch
语句.
示例
var num = 0;
for (var i = 1; i < 10; i++) {
if (i % 5 == 0) {
break;
}
num++;
}
console.log(num); // 4
尝试-抓住语句
接住
catch
子句包含try
块中抛出异常时要执行的语句.也就是,你想让try
语句中的执行操作成功,如果没成功,你想控制接下来发生的事情,这时你可以在catch
语句中实现.
如果有在try
块中有任何一个语句(或者从try
块中调用的函数)抛出异常,控制立即转向catch
子句.如果在try
块中没有异常抛出,会跳过catch
子句.
示例:
try {
console.log('1: start');
throw 'this is a error';
console.log('2: end');
} catch (err) {
console.log('3:', err);
}
// 输出顺序:
// 1:start
// 3:this is a error
catch
块指定一个标识符(在上面的示例中为err
)、该标识符保存由throw
语句指定的值.catch
块是唯一的,因为当输入catch
块时,JAVAJEL会创建此标识符,并将其添加到当前作用域;标识符仅在catch
块执行时存在;catch
块执行完成后,标识符不再可用.
从结果可以得知,如果在try
块中任何一个语句(或者从try
块中调用的和你熟)抛出异常,控制立即转向catch
子句.
总结
在本篇博客中,我们一起探索了脚本的基本语法。从变量和数据类型的定义开始,你已经了解了如何在脚本中处理数字、字符串、布尔值等不同类型的数据。接着,我们介绍了脚本中的运算符和表达式,使你能够进行数值计算和逻辑判断。条件语句和循环结构让你学会了根据不同的情况执行不同的代码,以及重复执行一段代码块.
脚本是一门非常强大且广泛应用的编程语言。掌握了这些基本的语法和概念,你已经具备了入门脚本编程的基础。未来,你将能够创建更加交互性的网页,实现更多惊艳的动态效果,甚至搭建出属于自己的WEB应用.但这只是一个开始,还有许多更深入的主题等待你去探索.
- 程序开发学习排行
-
- 1鸿蒙HarmonyOS:Web组件网页白屏检测
- 2HTTPS协议是安全传输,为啥还要再加密?
- 3HarmonyOS鸿蒙应用开发——数据持久化Preferences
- 4记解决MaterialButton背景颜色与设置值不同
- 5鸿蒙HarmonyOS实战-ArkUI组件(RelativeContainer)
- 6鸿蒙HarmonyOS实战-ArkUI组件(Stack)
- 7鸿蒙HarmonyOS实战-ArkUI组件(GridRow/GridCol)
- 8[Android][NDK][Cmake]一文搞懂Android项目中的Cmake
- 9鸿蒙HarmonyOS实战-ArkUI组件(mediaquery)
- 最近发表
-
- WooCommerce最好的WordPress常用插件下载博客插件模块的相关产品
- 羊驼机器人最好的WordPress常用插件下载博客插件模块
- IP信息记录器最好的WordPress常用插件下载博客插件模块
- Linkly for WooCommerce最好的WordPress常用插件下载博客插件模块
- 元素聚合器Forms最好的WordPress常用插件下载博客插件模块
- Promaker Chat 最好的WordPress通用插件下载 博客插件模块
- 自动更新发布日期最好的WordPress常用插件下载博客插件模块
- WordPress官方最好的获取回复WordPress常用插件下载博客插件模块
- Img to rss最好的wordpress常用插件下载博客插件模块
- WPMozo为Elementor最好的WordPress常用插件下载博客插件模块添加精简版