자바 스크립트 변수 참조 / 별칭


89

자바 스크립트에서 로컬 var에 별칭 / 참조를 할당하는 것이 가능합니까?

나는 C와 같은 것을 의미합니다.

function foo() {
  var x = 1;
  var y = &x;
  y++;
  alert(x); // prints 2 
}

= 편집하다 =

이 코드에서 arguments.callee 별칭을 사용할 수 있습니까? :

function foo() {
  arguments.callee.myStaticVar = arguments.callee.myStaticVar || 0;
  arguments.callee.myStaticVar++;
  return arguments.callee.myStaticVar;
}

5
간단한 대답은 아니오입니다. 하지만 SO에있는 사람이 :)을 할 수있는 해킹으로 올 것이라는 느낌했습니다
— Amarghosh

답변:


173

JavaScript에서 정수 및 문자열과 같은 기본 유형은 값으로 전달되는 반면 객체는 참조로 전달됩니다. 따라서이를 달성하려면 객체를 사용해야합니다.

// declare an object with property x
var obj = { x: 1 };
var aliasToObj = obj;
aliasToObj.x ++;
alert( obj.x ); // displays 2

그것은 빠르다 =) 내 함수 내에서 arguments.callee에 대한 별칭을 만들고 싶습니다 (매번 arguments.callee 입력을 피하기 위해). 이 방법으로 이것이 가능합니까? 이해하면 "인수"라는 별칭을 사용할 수 있지만 어쨌든 "callee"를 작성해야합니다. 그렇지 않습니까?
— gpilotino

9
@Darin : 이것은 그것을 약간 지나치게 단순화 한 것입니다. 원시 유형 대 객체가 아닌 불변 유형 대 가변 유형입니다. JavaScript에서 모든 것은 어떤 형태의 객체입니다.
— Crescent Fresh

7
JS에서 참조는 값으로 전달됩니다. "참조로 전달"과 "값으로 참조를 전달"에는 차이가 있습니다. Javascript에서 참조에 의한 매개 변수 전달은 지원되지 않습니다.
— Corneliu

15

어느 정도 가능하면 클로저를 사용하여 변수에 대한 별칭을 만들 수 있습니다.

Function.prototype.toString = function() {
    return this();
}

var x = 1;
var y = function() { return x }
x++;
alert(y); // prints 2, no need for () because of toString redefinition 

1
"alert (y); // prints 2"는 다음과 같아야합니다. "alert (y ()); // prints 2"결과를 얻으려면 실제로 함수를 호출해야합니다. 제안 된 구문이 특정 상황에서 도움이 될 것이기 때문에 너무 나쁩니다.
— Nathan Labenz 2013

3
그 toString 재정의에는 이유가 있으므로 alert(y)실제로 옳습니다. Function 프로토 타입 메서드를 재정의하는 것은 매우 나쁜 스타일입니다. 하지만 작동합니다!
— metalim

8

별칭을 사용할 수 있는지 여부는 데이터 유형에 따라 다릅니다. 객체, 배열 및 함수는 참조로 처리되며 앨리어싱이 가능합니다. 다른 유형은 본질적으로 원자 적이며 변수는 값에 대한 참조가 아닌 값을 저장합니다.

arguments.callee는 함수이므로 이에 대한 참조를 갖고 해당 공유 객체를 수정할 수 있습니다.

function foo() {
  var self = arguments.callee;
  self.myStaticVar = self.myStaticVar || 0;
  self.myStaticVar++;
  return self.myStaticVar;
}

위의 코드에서 말한다면 있음을 참고 self = function() {return 42;};한 후 self다음을 참조 할 다른 개체 보다 더 arguments.callee에 대한 참조를 유지 foo. 복합 객체가있는 경우 할당 연산자가 참조를 대체하지만 참조 된 객체는 변경되지 않습니다. 원자 값을 사용하는 경우와 같은 경우 는 변수에 '새로운'정수를 할당하는와 y++동일 y = y + 1합니다.


arguments.callee함수의 이름 인 별칭 이 이미 있다는 것은 말할 것도 없습니다 . 이 예에서는 그냥 사용할 수 있습니다 foo.myStaticVar(2009 년에는
— 그렇지 않았을까요

1

내 이전 답변 편집 : 함수 호출을 계산하려면 다음을 시도해 볼 수 있습니다.

var countMe = ( function() {
  var c = 0;

  return function() {
    c++;
    return c;
  }
})();

alert(countMe()); // Alerts "1"
alert(countMe()); // Alerts "2"

여기서 c는 카운터 역할을하며 arguments.callee를 사용할 필요가 없습니다.


또는 당신은 정적 변수 사용할 수 있습니다 countMe = function f(){ return ++f.c || (f.c = 1); }
— aljgom

1

user187291의 게시물을 확장 하면 getter / setter를 사용하여 함수를 사용해야하는 상황을 해결할 수도 있습니다.

var x = 1;
var ref = {
    get x()  { return x; },
    set x(v) { x = v; }
};
(ref.x)++;
console.log(x); // prints '2'
x--;
console.log(ref.x); // prints '1'

0

2019 년에는 축소 된 jquery 플러그인을 작성해야 하므로이 별칭이 필요하므로 다른 소스에서 이러한 예제와 기타를 테스트하여 전체 객체의 메모리에 복사하지 않고 참조 만 생성하는 방법을 찾았습니다. 나는 이미 파이어 폭스로 이것을 테스트하고 전에 파이어 폭스에서 작업 관리자의 탭 메모리를 보았습니다. 코드는 다음과 같습니다.

var {p: d} ={p: document};
console.log(d.body);

이것은 참조로 아무것도 전달하지 않으며 문서를 직접 전달할 수 있습니다 (이미 객체에 대한 참조이며 값으로 전달됨). 구조 해제는 별칭을 생성하지 않습니다.
— 모니카 기억
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.