代入されていない変数のデフォルト値は未定義であることをあらかじめ宣言します。
1.EC変数リフティング var a;
2.グローバル変数を宣言し、VO(G)に格納します。
3.宣言されたグローバル変数は、同じプロパティwindow.aをグローバルオブジェクトGO(window)にも設定します。
4.後に、グローバルオブジェクトであろうとグローバル変数であろうと、一方が変わればもう一方も一緒に変わります
エラー: 変数が宣言されていません
グローバルで、変数を出力し、まず、それがグローバル変数[VO(G)]であるかどうかを確認し、そうでない場合は、それがグローバルオブジェクトオブジェクト[GO->window]のプロパティであるかどうかを確認し続け、どちらでもない場合は、エラーを報告します:変数が定義されていません Uncaught ReferenceError: a is not defined
グローバルオブジェクトGOストレージ値へ
window.a = 13;
//=>グローバルオブジェクトGOにプロパティを設定する
console.log(a);
//=>13 aはGOの特性である=> window.a
a = 14; //=>window.a=14
console.log(a); //=>14
LET とVARの違い
1.LET/CONST/CLASS/IMPORTやES6で変数を作成する他の方法に基づいて、変数のリフティングはありません。
計算
console.log(a, b, c);//=>undefined*3
var a = 12,
b = 13,
c = 14;
function fn(a) {
console.log(a, b, c);//=>10 13 14
a = 100;
c = 200;
console.log(a, b, c);//=>100 13 200
}
b = fn(10);//=>returnを書かずに実行された関数は未定義の結果を返す
console.log(a, b, c);//=>12 undefined 200
計算に関する質問
var ary = [12, 23];//=>AAAFFF000 [100,23]
function fn(ary) {//=>AAAFFF111
console.log(ary);//AAAFFF111
ary[0] = 100;
ary = ;//=>AAAFFF222 [0]
ary[0] = 0;
console.log(ary);[0]
}
fn(ary);
console.log(ary);[100,23]
計算
一般的な関数の実行は、コンテキストの形成は、関数の実行では、メモリの最適化を確保するために、スタックにリリースされます。しかし、現在のコンテキストで何かが、占有外の変数のコンテキストによって、それはスタックにリリースすることはできません場合は、プライベート変数のコンテキストに保存され
スコープチェーンは、関数が作成されたときの[スコープ]に関係するだけで、将来のスコープチェーンがどこを指すかを決めるもので、関数が実行される場所とは関係ありません。
計算
var a=1;
var obj ={
"name":"tom"
}
function fn(){
var a2 = a;
obj2 = obj;
a2 =a;
obj2.name =”jack”;
}
fn();
console.log(a);//=>1
console.log(obj);//=>{name:"jack"}
計算
var x = 100,
y = 100;
function fn() {
// プライベート・コンテキストEC
// AO(FN) y=200
var y = 200;
console.log(x); //=>100 グローバル変数
x=1000; //=>グローバルxを1000に変更する
console.log(y); //=>200 プライベート変数
//console.log(z); //=>Uncaught ReferenceError: z is not defined
z = 300; //=>window.z=300
}
fn();
console.log(window.z); //=>300
計算
var a = 1;
function fn(a) {
console.log(a);
var a = 2;
function a() {}
console.log(a);
}
fn(a);
console.log(a);
/*
* EC(G)グローバル・コンテキスト
* VO(G)グローバル変数オブジェクト(計算)
* var a;
* function fn(a){...}; fn[[scope]]=EC(G)
*/
var a = 1; //=> =1
function fn(a) {
/*
* プライベート・コンテキストEC
* AO(FN)プライベート変数オブジェクト
* a = 1
* =
* = 2
* SCOPE-CHAIN:<EC(FN),EC(G)>
* 形式的パラメータ割り当て: a=1
* 変数リフティング:
* var a;((今はAOがあるから意味がない)。
* a = ; ここでの操作は、やはりAOのaの値を関数に変更するものである。
*/
console.log(a); //=>
var a = 2; //=>a=2 プライベートaを2に変更する
function a() {}
console.log(a); //=>2
}
fn(a);
//=>グローバル関数fnは、実パラメータ "グローバル変数aの値 "を渡して実行される。”
//=>fn(1)
console.log(a); //=>1
計算
console.log(a);
var a=12;
function fn(){
console.log(a);
var a=13;
}
fn();
console.log(a);
/!*
* EC(G)グローバル・コンテキスト
* var a;
* function fn(){...};
*!/
console.log(a); //=>undefined
var a=12; //=>グローバル変数 a=12
function fn(){
/!*
* EC(FN)プライベート・コンテキスト
* var a;
*!/
console.log(a); //=>undefined
var a=13; //=>プライベート変数a=13
}
fn();
console.log(a); //=>グローバル変数aの値は12である。
変数のリフティングと関数
console.log(a);
var a=12;
function fn(){
console.log(a);
a=13;
}
fn();
console.log(a);
/!*
* EC(G)グローバル・コンテキスト
* var a;
* function fn(){...};
*!/
console.log(a); //=>undefined
var a=12;// =12
function fn(){
/!*
* EC(FN)プライベート・コンテキスト
*!/
console.log(a);
//=>自分のプライベート変数ではなく、EC12でグローバル変数を見つけた
a=13;// =13
}
fn();
console.log(a); //=>13
計算
console.log(a);
a=12;
function fn(){
console.log(a);
a=13;
}
fn();
console.log(a);
/!*
* EC(G)グローバル・コンテキスト
* function fn(){...};
*!/
console.log(a);//=>Uncaught ReferenceError: a is not defined
a=12;
function fn(){
console.log(a);
a=13;
}
fn();
console.log(a);
計算
var a=10,b=11,c=12;
function test(a){
a=1;
var b=2;
c=3;
}
test(10);
console.log(a);
console.log(b);
console.log(c);
/!*
* EC(G)グローバル・コンテキスト
* var a; var b; var c;
* function test(){...}; test[[scope]]=EC(G);
*!/
var a=10,b=11,c=12; // =10 b=11 c=12
function test(a){
/!*
*EC(TEST)プライベート・コンテキスト
*((関数本体で宣言された正式なパラメータと変数はプライベートである)
* a = 10
* b
* SCOPE-CHAIN:<EC(TEST),EC(G)>
* 正式なパラメータ割り当て: a=10
* 変数のリフティング: var b;
*!/
a=1; // =1
var b=2; // =2
c=3; // =3
}
test(10);
console.log(a); //=>10
console.log(b); //=>11
console.log(c); //=>3
条件判断
if (!("a" in window)) {
}
console.log(a);
/!*
* EC(G)グローバル・コンテキスト
* var a;
* グローバル変数VOを宣言する
* プロパティ・ウィンドウをGOに設定する.a
*!/
if (!("a" in window)) { // "a" in window => undefined=>!false=>true
var a = 1;
}
console.log(a); //=>undefined
計算
var a = 4;
function b(x, y, a) {
console.log(a);
arguments[2] = 10;
console.log(a);
}
a = b(1, 2, 3);
console.log(a);
/!*
* EC(G)グローバル・コンテキスト
* var a;
* function b(x,y,a){...}; b[[scope]]=EC(G);
*!/
var a = 4; // =4
function b(x, y, a) {
/!*
* EC(B)プライベート・コンテキスト
* x=1
* y=2
* a=3
*
* 1.SCOPE-CHAIN:<EC(B),EC(G)>
* 2.this "を初期化する。
* 3.アルゴリズムの初期化= { 0:1, 1:2, 2:3, length:3 }
* 4.正式なパラメータ割り当て:x/y/aにそれぞれ値を割り当てる。
* 5.変数リフティング
* 6.コード実行
*
* JSの非厳密モードでは、ARGUMENTSと形式変数の間にマッピングメカニズムがある(どちらも渡された実パラメータに関する情報を格納するために使用されるため)。
* //=>,ARGUMENTS形式パラメータが定義されているかどうかに関係なく存在し、形式パラメータを定義した後は、形式パラメータは渡された値にアクセスできるだけでなく
* //=>,ARGUMENTS(渡された値は計算にも格納され、この時点で両者間のマッピングメカニズムが存在する)。
* 最初の形式変数 マッピング 論証[0]
* 番目の形式パラメータは、ARGUMENTSをマッピングする。[1]
* ...
* マッピング:フォーマル・パラメータがその値を変えようが、ARGUMENTSが各項目の値を変えようが、それらは互いに変化する。
*!/
console.log(a); //=>3
arguments[2] = 10;
//=>ARGUMENTSのインデックスを2から10に変更すると、マッピングメカニズムにより、正式パラメータaの値が10に変更される。
console.log(a); //=>10
}
a = b(1, 2, 3);
//b関数を実行し、関数に1,2,3個の実数パラメータを渡し、関数実行の戻り値をグローバル変数aに代入する。
=> =undefined,関数は戻り値を書かないので
console.log(a); //=>undefined
計算
function fn(x, y, z) {
console.log(x, y, z, arguments);
arguments[0] = 100;
y = 200;
arguments[2] = 300;
console.log(x, y, z, arguments);
}
fn(10, 20, 30);
function fn(x, y, z) {
console.log(x, y, z, arguments);
// => x=10 y=20 z=30
// => arguments = [10,20,30]
arguments[0] = 100; //[100,20,30] x=100
y = 200; //y=200 [100,200,30]
arguments[2] = 300; //[100,200,300] z=300
console.log(x, y, z, arguments);
// => x=100 y=200 z=300
// => arguments = [100,200,300]
}
fn(10, 20, 30);
計算
"use strict";
function fn(x) {
console.log(x);
arguments[0] = 100;
console.log(x);
}
fn(10);
"use strict";
//=>JSストリクトモードを使う
function fn(x) {
console.log(x); //=>10
arguments[0] = 100;
//ストリクトJSモードでは、マッピング・メカニズムは存在しない。
console.log(x); //=>10
}
fn(10);
計算
var foo = 'hello';
(function (foo) {
console.log(foo);
var foo = foo || 'world';
console.log(foo);
})(foo);
console.log(foo);
/!*
* EC(G)グローバル・コンテキスト
* var foo;
*!/
var foo = 'hello'; //グローバル・フー='hello'
(function (foo) {
/!*
* EC(AN)プライベート・コンテキスト
* foo = 'hello'
*これはプライベート変数で、グローバル変数とは異なるが、グローバル値が与えられているので、この時点で2つの変数は同じ値を持つ。,
*しかし、同じ変数ではない
*
* SCOPE-CHAIN:<EC(AN),EC(G)>
* イニシャル this/アーギュメント
* 形式的パラメータ割り当て:fooに値を代入する
* 変数リフティング:var foo;((すでに宣言されている)
* コード実行
*!/
console.log(foo); //=>'hello'
var foo = foo || 'world'; //foo='hello' || 'word'='hello'
console.log(foo); //=>'hello'
})(foo); //自己実行関数は、グローバルfooの値を実パラメータとして関数に渡して実行する。...('hello')
console.log(foo); //=>'hello'





