JavaScript基本数据类型(8)- JS栈内存和堆内存详解

JS栈内存和堆内存详解

上章节详细讲解了JavaScript底层的运行机制,这章节就好好来讨论下js代码运行开辟出的 堆和栈,以及变量之间复制,诸如 var a = 10; a = b; 这类代码的原理

栈内存:拥有作用域,代码执行空间,存储基本值和变量

  1. 提供一个供 JavaScript 代码自上而下执行的 window 全局栈内存(代码都是在栈中执行的)
  2. 基本数据类型会直接在栈内存中存放的,引用数据类型会开辟一个堆内存类存放,并且用指针指向其地址

堆内存:引用值存储空间

  1. 存储引用类型值的(对象:键值对形式,函数:字符串形式)

    => 当前堆内存如果释放,那么这个引用空间就会彻底销毁,包括里面所有值

    => 堆内存的释放:如果还有变量指向该内存,就不会释放,只要还有一个变量指向,就不会释放(类python)

    => 变量 = null ,也是一个不错的内存释放方法,一个变量如果指向 null,也就是指向空对象指针,原有被指向的对象就是少一层指向

    在这里插入图片描述

复制变量值的区别

基本类型值的复制

下面这段代码,能把基本类型变量的复制解释清楚

var a = 10;
var b = a;
// 基本类型复制

在这里插入图片描述

复杂数据类型的复制

下面这段代码,能把应用类型变量的复制解释清楚

var m = {name: 'xyb'};
var n = m;
// 基本类型复制

在这里插入图片描述

复制变量值练习

这个案例能很好体现 基本类型的复制 引用类型的复制

  • 已知下面代码可以修改BOX元素的样式

    box.style.color = 'green';
    
  • 那么下面的写法是否可以修改元素的样式,如果不可以是为什么?

    //第一种方案
    let AA = box.style;
    AA.color = 'red';
    
    //第二种方案
    let BB = box.style.color;
    BB = 'red';
    
    //=>哪种方式可以实现,不能实现是因为啥?
    

第一种可以:对指针内栈内存里的值进行操作,JS会基于DOM映射机制把页面元素进行重新渲染

第二种不可以:其只是把box.style.color的值复制了一份新的而已,并且只改变了本身BB变量的指向
在这里插入图片描述

内存地址小练习

let n = [10, 20];
let m = n;
let x = m;
m[0] = 100;
// m ,n, x [100, 20]
n = [30, 40];
// n, [30, 40]  m, x [100, 20]
n[0] = 200;
// n, [200, 40]  m, x [100, 20]
x[0] = 200;
// n, [200, 40]  m, x [200, 20]
m = [50, 60];
// n [200, 40]  x [200, 20] m [50, 60]
m = x;
// n [200, 40]  x m [200, 20]
m[1] = 300;
// n [200, 40]  x m [200, 300]
n[2] = 400;
// n [200, 40, 400]  x m [200, 300]
console.log('n: ' + n);
console.log('m: ' + m);
console.log('x: ' + x);

大公司面试题

  1. 阿里

    let a = {
        n: 1
    };
    let b = a;
    a.x = a = {
        n: 2
    };
    console.log(a.x);
    console.log(b);
    

    在这里插入图片描述

  2. 腾讯

    var a = 'abc' + 123 + 456;
    var b = '456' - '123';
    var c = 100 + true + 21.2 + null + undefined + "Tencent" + [] + null + 9 + false;
    console.log(a, b, c);
    
    // a = 'abc123456';
    // b = 333;
    // c = 'NaNTencentnull9false'
    
  3. 腾讯

    var str = 'abc123';
    var num = parseInt(str);
    if (num == NaN) {
        alert(NaN);
    } else if (num == 123) {
        alert(123);
    } else if (typeof num == 'number') {
        alert('number');
    } else {
        alert('str');
    }
    
    // 弹出 Number
    
  4. 腾讯

    var a = 0;
    var b = a;
    b++;
    alert(a)
    var o = {};
    o.a = 0;
    var b = o;
    b.a = 10;
    alert(o.a)
    

    在这里插入图片描述

  5. 输出 ‘1’ 的值

    alert(1)          
    console.log(parseInt(1.3))              
    console.log(1)  
    console.log(isNaN(1))   
    console.log(parseInt("1"))
    
    // 1 2 3 5
    
  6. 输出 ‘undefined’ 的值

    alert(1)
    typeof undefined
    parseInt(undefined)
    isNaN(undefined)
    
    // 2
    
  7. 输出 true 的值

    isNaN(null)
    isNaN(parseInt(null))
    Number(null)
    parseFloat(null)
    
    // 2
    
  8. 输出下面的结果

    parseInt("")		// NaN
    Number("")			// 0
    isNaN("")			// 0		isNaN(Number(""))
    parseInt(null)		// NaN		parseInt(String(null))
    Number(null)		// 0	
    isNaN(null)			// false	isNaN(Number(null)) 
    parseInt("12px")  	// 12
    Number("12px")		// NaN
    isNaN("12px")		// true
    
  9. 输出下面的结果

    if (isNaN(NaN) == "") {
        console.log("哈哈")
    } else {
        console.log("呵呵")		// 输出 呵呵
    }
    
  10. 输出下面的结果

    let x = [1, 2, 3];
    let y = x;
    let z = [4, 5, 6];
    y[0] = 10;
    y = z;
    z[1] = 20;
    x[2] = z = 30;
    console.log(x, y, z);
    
    // x = [10, 2, 30]
    // y = [4, 20, 6]
    // z = 30
    
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值