JS的语法琐碎知识点 快速复习

变量提升

        JavaScript 引擎的工作方式是,先解析代码,获取所有被声明的变量,然后再一行一行地运行。这造成的结果,就是所有的变量的声明语句,都会被提升到代码的头部,这就叫做变量提升。

console.log(msg);
	var msg = 'so easy';
	// 变量提升,相当于下面的代码
	var msg;
	console.log(msg);
	msg = 'so easy';
	// 说明: 最后的结果是显示undefined, 表示变量msg已声明, 但还未赋值。

注意:变量可以不用var声明,直接写出来,变量提升只对 var 命令声明的变量有效,如果一个变量不是用 var 命令声明的,就不会发生变量提升。以下代码会报错,提示“ReferenceError: msg is not defined”,即变量 msg 未声明,这是因为 msg 不是用 var 命令声明的,JavaScript引擎不会将其提升。

	console.log(error_msg);//会报错
	error_msg = 'error';//可以不用var直接写出来声明一个对象

数据类型

js有6种数据类型:其中有五种简单的数据类型:undefinedNull布尔数值字符串。一种复杂数据类型Object

数  值(Number): 整数和小数(比如 1 和 3.14)

字符串(String): 字符组成的文本(比如"Hello World")

布尔值(Boolean):true(真)和 false(假)两个特定值

undefined:       表示“未定义”或不存在,即此处目前没有任何值

Null:             表示空缺,即此处应该有一个值,但目前为空

对象(object)(引用) : 各种值组成的集合

   a. 对象(object){name:”zhangsan”,age:”18”}

   b. 数组(array)[1,2,3]

   c. 函数(function)function test() {}

多个数据可以在一个语句中打印,用逗号分隔

函数中的变量声明可以不写,毕竟都是var,如果是标识符,在函数中可以不写引号

NULL

        null类型是只有一个值的数据类型,即特殊的值null。它表示空值,即该处的值现在为空,它表示一个空对象引用。

使用Null类型值时注意以下几点:

        a. 使用typeof操作符测试null返回object字符串。

        b. undefined派生自null,所以等值比较返回值是true。所以,未初始化的变量和赋值为null的变量相等。

console.log(undefined == null);

var box = null;  // 赋值为null的变量

var a;  // 未初始化的变量

console.log(a == box);  // 两个的值相等

Boolean

                                                                            

字符串

转为true的值

转为false的值

Boolean

true

false

String

非空字符串

空字符串

Number

非0数字(包括无穷大)

0和NaN

Object

任何对象

null

undefined

 

undefined

java中两边的操作数只能为booelan类型
*       js中两边的操作数可以为其他类型
*           如果两边的操作数为其他类型,非boolean类型的数据出现的时候
*               结果肯定为其中一个操作数之一
依据短路原则,&&第一个为假,第二个就遍历不到,所以值为第一个值
            ||第一个为真,第二个就遍历不到,所以结果为第一个值
*               &&   第一个操作数转为boolean,如果为false,结果为第一个操作数
*                    如果为true,结果为第二个操作数
*               ||   第一个操作数转为boolean,如果为false,结果为第二个操作数
*                    如果为true,结果为第一个操作数

JavaScript 使用大括号,将多个相关的语句组合在一起,称为“区块”。JS中只有函数才有作用于作用域

与大多数编程语言不一样,JavaScript 的区块不构成单独的作用域。也就是说,区块中的变量与区块外的变量,属于同一个作用域。

{
		var a = 10;
	}
	console.log("a-----" + a);
//10   可以获取到

上面的代码,在区块内部声明并赋值了变量a,然后在区块外部,变量a依然有效,这说明区块不构成单独的作用域,与不使用区块的情况没有任何区别。所以,单独使用的区块在 JavaScript 中意义不大,很少出现。区块往往用来构成其他更复杂的语法结构,比如 for、if、while等。

数组

特别灵活,不会发生数组越界,越界的会报undefined

遍历方式

普通for循环

var arr = [1, '2', 3.3, true, null];
	for (var i = 0; i < arr.length; i++) {
		console.log(arr[i]);
	}

for in 循环(类似foreach循环,但是一个是访问下标,一个是获得整个元素)

var arr = [1, '2', 3.3, true, null];
	for (var i in arr) {
		console.log(arr[i]);
	}

forEach函数

//数组名.forEach(function(element, index){
//数组名[下标]是获取元素
})    // element(名称任意):元素,index(名称任意):下标
    var arr = [1, '2', 3.3, true, null];
	arr.forEach(function(element, idx) {
		console.log(idx + "-->" + element);
	});

数组的属性:

如果下标为正常的平时使用的时候(整数字符串也可以),没有的显示undefined,有就显示应该的

负数,小数,非数字字符串,这些不计算在长度里面,当成"属性"处理,相当于自定义属性

* for --> 不遍历属性

* foreach -->不遍历属性和索引中的undefined

* for in -->不遍历索引中的undefined

var arr = [1, '2', 3.3, true, null];
	arr[-1.5] = '我是数组的属性';
	arr['sxt'] = 'sxt';
	console.log(arr[-1.5]);
	console.log(arr['sxt']);
	console.log(arr[-1]);
	console.log(arr['1']);  // 自动转换为1

//结果为: 
我是数组的属性
sxt
undefined
2   (字符串)

数组提供的操作方法

Array对象为我们提供了一些方法,可以很方便地操作数组

push          添加元素到最后

unshift       添加元素到最前

pop           删除最后一项

shift         删除第一项

reverse       数组翻转

join          数组转成字符串

indexOf       数组元素索引

slice         截取(切片)数组,原数组不发生变化

        一个参数为从当前位置开始截取到最后

        二个参数为从第一个开始截取到第二个参数

splice        剪接数组,原数组变化,可以实现前后删除效果,被截取下来的从原来的数组中消失

         一个参数表示当前位置开始截取到最后

         二个参数从第一个开始截取第二个参数个

         多个参数表示从  开始截取的地方从第三个及以后的填补被截取下来的原数组的内容

concat        数组合并

函数

有三种函数定义的方式:函数声明语句、函数定义表达式、Function构造函数

函数在传递参数的时候可以多传递也可以少传递,多传递选前面的,少传递其他的用undefined

 

声明函数

	// 声明函数
	function foo1() {
		console.log('foo1');
	}			
	// 调用函数
	foo1();

函数定义表达式

以表达式方式定义的函数,函数的名称是可以不需要的 ,这种写法将一个匿名函数赋值给变量。这时,这个匿名函数又称函数表达式,因为赋值语句的等号右侧只能放表达式。

	foo2();
    // 声明函数
	var foo2 = function () {
		console.log('foo2');
	}
	// 调用函数
	foo2();

函数也有提升问题,因为JS是把所有的东西都加载完了再去执行代码的,所以也有类型提升,第一个也可以执行

//函数表达式
        var fn1= function func(i){
            console.log("我是函数表达式1");
            if(i==5){
                return;
            }
            i++;
            func(i);
        };
        console.log(fn1);
        fn1(1);
      //  func();

这是递归        这种方式不能用func(8)这种方式来执行,只能用fn(1)来执行,打印fn1就是这个函数体

//直接调用
        var fn2=function(){
            console.log("我是函数表达式2");
        }();
        //fn2();报错

上述代码创建完了就调用了,所以fn2毫无意义,会报错

几种特殊的调用函数的方式:

//几种特殊的运用方式
!function fff(a){
            console.log(1234);
        }(1);
        ~function fff1(a){
            console.log(456);
        }(1);
        +function fff2(a){
            console.log(789);
        }(1);
        -function fff3(a){
            console.log(234);
        }(12);
        (function fff4(a){
            console.log('haha');
        })(1);

关于函数内部的作用域问题,注意!!!!

<script>
        // 若函数形参同名(一般不会这么干):在使用时以最后一个值为准
        function add2(a, a) {
            console.log('函数形参同名-----' + a);
        }
        add2(1, 2);
        // 给参数默认值
        function func(a=1, b=2) {
            return a + b;
        }
        console.log('参数默认值-----' + func(4,5));

        // 给形参o赋予了新的数组
        var obj2 = [1, 2, 3];
        function paramter2(o) {
           // o = [2, 3, 4];
            o[0] = 3;
        }
        paramter2(obj2);
        console.log('引用传递-----' + obj2);
    </script>

第一个函数测试的是参数同名,按照第二个来,第二个函数测试的是给参数值赋予默认值,第三个函数测试的是值传递,注意,java中只有传递值(个人觉得是地址值),如果是基本数据类型,就把常量池中的数据赋予给变量,在函数内部,作为局部变量,当变量重新赋值,或着说字符串(一个字符串用""书写的默认是一个字符串对象)或着是其他的引用类型  就会相当于把变量重新给一个新的对象,所以在函数外部的数据是不会变化的,但是作为数组,通过索引改变数据,会改变数据,所以外部的对象指向的那个对象其实已经被修改了

 

JS中的this关键字

this 指代对象
    运行期为this绑定对象
    决策树: 判定this指代的是哪一个对象
        1.this所在的函数是通过new的使用调用么,如果是this指代new的对象
        2.this 所在的函数是通过 XX.调用的么,如果是,this指代调用的对象 .前面的对象
        3.如果都不是,默认this指代window(全局对象)

        定义的全局变量默认相当于window对象的一个属性
        定义的全局的方法,默认相当于window对象的功能
  <script>
        var a=1;
        console.log(a);
        console.log(window.a);
        console.log(this.a);

        var obj= {
            a:12,
            fn:function(x,y){
                console.log(this.a,x,y)
            }
        };

        obj.fn(3,4);
        var f=obj.fn;
        f();
        window.f();
        function Person(name,age){
            this.name=name;
            this.age=age;
        }

        var p1=new Person('zhangsan',18);
        var p2=new Person('zhangsan2',19);
        console.log(p1);
        console.log(p2);

        var obj2={
            a:24
        };

        //apply()和call() 指定当前函数在调用的时候,内部的this知道哪一个对象
        // 第一个参数就是指代的对象, call()第二个到多个参数为为调用函数的实参,apply方法的第二个参数为[],数组中存放实参
        obj.fn();

        obj.fn.call(obj2,2,3);
        obj.fn.apply(obj2,[2,3]);
        obj.fn();

        //arguments 函数内置对象,在函数内部使用,动态的指定当前调用函数时传递的参数,操作数组的方式使用
//arguments 可以获取调取对象的参数值所有,包括没有真正传入到函数中的(函数的接收的变量个数不够)
        function haha(){
            console.log(arguments); 
            for(var i in arguments){
                console.log(arguments[i]);
            }
        }

        haha(1,2,3,4,5);
    </script>

apply()和call()方法,指定当前函数在调用的时候,内部的this知道哪一个对象

第一个参数就是指代的对象, call()第二个到多个参数为为调用函数的实参,apply方法的第二个参数为[],数组中存放实参

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值