>  기사  >  웹 프론트엔드  >  js 변수, 범위, 메모리에 대한 자세한 설명_기본 지식

js 변수, 범위, 메모리에 대한 자세한 설명_기본 지식

WBOY
WBOY원래의
2016-05-16 16:35:581195검색

기본 유형 값에는 정의되지 않음, NUll, Boolean, Number 및 String이 포함됩니다. 이러한 유형은 메모리에서 고정된 크기 공간을 차지하며 해당 값은 스택 공간에 저장되며 값으로 액세스합니다.

(1) 값 유형: 숫자 값, 부울 값, null, 정의되지 않음.
(2) 참조 유형: 객체, 배열, 함수.

할당된 값이 참조 유형인 경우 힙 메모리에 이 값에 대한 공간을 할당해야 합니다. 이러한 값의 크기는 고정되어 있지 않기 때문에(객체에는 많은 속성과 메서드가 있음) 스택 메모리에 저장할 수 없습니다. 하지만 메모리 주소 크기는 고정되어 있으므로 메모리 주소를 스택 메모리에 저장할 수 있습니다.

<script type="text/javascript”>
var box = new Object(); //创建一个引用类型
var box = "lee";  //基本类型值是字符串
box.age = 23;  //基本类型值添加属性很怪异,因为只有对象才可以添加属性。
alert(box.age); //不是引用类型,无法输出;
</script>

간단히 말하면 힙 메모리는 참조 값을 저장하고, 스택 메모리는 고정형 값을 저장합니다.

<script type="text/javascript">
  var man = new Object();//man指向了栈内存的空间地址
  man.name = "Jack";
  var man2 = man;//man2获得了man的指向地址

  alert(man2.name);//两个都弹出Jack
  alert(man.name);
</script>

변수 값 복사

다음 예를 살펴보세요.

<script type="text/javascript">
  var man = new Object();//man指向了栈内存的空间地址
  man.name = "Jack";
  var man2 = man;//man2获得了man的指向地址

  man2.name = "ming";//因为他们都指向同一个object,同一个name,不管修改谁,大家都修改了
  alert(man2.name);//两个都弹出ming
  alert(man.name);
</script>

위에서 결론을 내릴 수 있습니다. 변수 복사의 경우 기본 유형과 참조 유형도 다릅니다. 기본 유형은 값 자체를 복사하고 참조 유형은 주소를 복사합니다.

패스 매개변수

ECMAScript에서는 모든 함수 매개변수가 값으로 전달됩니다.

<script type="text/javascript">
   function box(num){   //按值传递
     num+=10;
     return num;
   }

   var num = 10;
   var result = box(num);
   alert(result); //如果是按引用传递,那么函数里的num会成为类似全局变量,把外面的number替换掉
   alert(num);  //也就是说,最后应该输出20(这里输出10)
</script>

Javascript는 참조로 전달하지 않습니다. 참조로 전달이 있는 경우 함수 내의 변수는 전역 변수가 되며 외부에서도 액세스할 수 있습니다. 그러나 이것은 분명히 불가능하다.

실행 환경 및 범위

실행 환경은 JavaScript에서 가장 중요한 개념 중 하나입니다. 실행 환경은 다른 데이터에 액세스하기 위한 변수나 함수의 권한을 정의합니다.

전역 실행 환경은 웹 브라우저에서 가장 주변적인 실행 환경입니다. 따라서 전역 변수의 모든 기능은 창의 속성과 메서드로 생성됩니다.

<script type="text/javascript">
   var name = "Jack";      //定义全局变量
   function setName(){
     return "trigkit4";
   }

   alert(window.name);    //全局变量,最外围,属于window属性
   alert(window.setName()); //全局函数,最外围,属于window方法
</script>

실행환경의 코드가 실행되면 환경은 소멸되며, 그 안에 저장된 변수와 함수도 소멸됩니다. 글로벌 환경이라면 모든 프로그램이 실행되거나 종료될 때까지 소멸되지 않습니다. 웹페이지가 완성되었습니다.

var의 지역변수 제거

<script type="text/javascript">
   var name = "Jack";
   function setName(){
     name = "trigkit4";  //去掉var变成了全局变量
   }

   setName();
   alert(name);//弹出trigkit4
</script>

매개변수를 전달하면 지역변수이기도 합니다

<script type="text/javascript">
   var name = "Jack";
   function setName(name){  //通过传参,也是局部变量
     alert(name);
   }

   setName("&#65532;trigkit4");//弹出trigkit4
   alert(name);//弹出Jack
</script>

함수 본문에도 함수가 포함되어 있습니다. 이 함수만 함수의 내부 계층에 액세스할 수 있습니다.

<script type="text/javascript">
   var name = "Jack";
   function setName(){
     function setYear(){  //setYear()方法的作用域在setName()内
       return 21;
     }
   }
   alert(setYear());//无法访问,出错 
</script>

다음 방법을 통해 액세스할 수 있습니다:

<script type="text/javascript">
   var name = "Jack";
   function setName(){
     function setYear(){  //setYear()方法的作用域在setName()内
       return 21;
     }
     return setYear();
   }
   alert(setName()); //弹出21
</script>

또 다른 범위 예:

<script type="text/javascript">
   var name = "Jack";
   function setName(){
     function setYear(){  //setYear()方法的作用域在setName()内
       var b = "hi";   //变量b的作用域在setYear()内
       return 21;
     }
     alert(b);//无法访问 
   }
</script>

환경에서 코드가 실행되면 범위 체인이라는 것이 형성됩니다. 그 목적은 실행 환경에서 액세스 권한이 있는 변수 및 함수에 대한 질서 있는 액세스를 보장하는 것입니다(액세스할 규칙 계층 참조). , 범위 체인의 프런트 엔드는 실행 환경의 변수 개체입니다.

범위

함수 내에서 선언되지 않거나 var 없이 선언된 변수는 전역 범위를 갖습니다. 창 개체의 모든 속성은 코드 내 어디에서나 액세스할 수 있습니다. 함수 내부에서 var로 장식됩니다. 변수는 지역 변수이며 함수 본문 내에서만 사용할 수 있습니다. 함수의 매개변수는 var를 사용하지 않지만 여전히 지역 변수입니다.

블록 범위 없음

블록 범위 없음

// if语句:

<script type="text/javascript">
if(true){            //if语句的花括号没有作用域的功能。

var box = "trigkit4";
}
alert(box);//弹出 trigkit4
</script>


for 루프 문에도 마찬가지입니다.

변수 쿼리

변수 쿼리에서는 지역 변수에 액세스하는 것이 전역 변수보다 빠르므로 범위 체인을 검색할 필요가 없습니다.
아래 예:

<script type="text/javascript">
   var name = "Jack";
   function setName(){
      var name = "trigkit4";
      return name; //从底层向上搜索变量
  }
  alert(setName());   
</script>

메모리 문제

Javascript에는 자동 가비지 수집 메커니즘이 있으므로 데이터가 더 이상 사용되지 않으면 "null"로 설정하여 참조를 해제할 수 있습니다.

참고문헌

아주 간단한 예: DOM 객체는 Javascript 객체에 의해 참조되는 동시에 동일하거나 다른 Javascript 객체를 참조합니다. 이 DOM 객체는 메모리 누수를 일으킬 수 있습니다. 이 DOM 개체에 대한 참조는 스크립트가 중지될 때 가비지 수집기에 의해 회수되지 않습니다. 참조 순환을 끊으려면 DOM 요소를 참조하는 객체나 DOM 객체에 대한 참조를 null로 할당해야 합니다.

폐업

클로저 외부의 변수가 클로저에 도입되면 클로저가 종료될 때 객체를 가비지 수집(GC)할 수 없습니다.

var a = function() {
 var largeStr = new Array(1000000).join('x');
 return function() {
  return largeStr;
 }
}();

DOM 유출

원본 COM이 제거되면 제거되지 않는 한 하위 노드 참조를 재활용할 수 없습니다.

var select = document.querySelector;
var treeRef = select('#tree');

//在COM树中leafRef是treeFre的一个子结点
var leafRef = select('#leaf'); 
var body = select('body');

body.removeChild(treeRef);

//#tree不能被回收入,因为treeRef还在
//解决方法:
treeRef = null;

//tree还不能被回收,因为叶子结果leafRef还在
leafRef = null;

//现在#tree可以被释放了。

타이머 유출

타이머는 메모리 누수가 흔히 발생하는 장소이기도 합니다.

for (var i = 0; i < 90000; i++) {
 var buggyObject = {
  callAgain: function() {
   var ref = this;
   var val = setTimeout(function() {
    ref.callAgain();
   }, 90000);
  }
 }

 buggyObject.callAgain();
 //虽然你想回收但是timer还在
 buggyObject = null;
}

디버그 메모리

Chrome에 내장된 메모리 디버깅 도구를 사용하면 메모리 사용량과 메모리 누수를 쉽게 확인할 수 있습니다.
타임라인에서 기록 클릭 ->

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.