javascript:withの使い方及び延長作用ドメインチェーン

2716 ワード

「オリジナル記事は、転載してください.http://lllt.iteye.comから来ました.」
 
    「Javascript高級プログラム設計(第二版)」の66ページでは、「with文の変数オブジェクトは読み取り専用であるため、urlは関数実行環境の一部となり、関数としての値が返されます.」と書かれていますが、読み終わったら誰が霧を感じますか?
 
    まず彼の例を見てみます.
 
function buildUrl(){
     var qs="?debug=true";
     with(location){
          var url=href+qs;
     }
     return url;
}
var result=buildUrl();

alert(result);
 
    もし本を読んでいないなら、javascriptを勉強したいです.この例を考えて実行してみてください.
 
    最後にポップアップしたのはundefinedではなく、あなたの静的ページアドレス+qsの値です.
 
with文の役割を見てください.
 
    通俗的には、オブジェクトを参照して、そのオブジェクトの属性を操作することで、そのオブジェクト名を重複して書くことを省略し、簡略化して書くことができるという役割を果たします.
 
いくつかの問題があります.
 
   1、withコードブロックにおいて、javascriptエンジンの変数に対する処理方式は、まず対象の属性であるかどうかを調べ、もしそうであれば停止する.継続的に検索しない場合は、ローカル変数ですか?(「Javascript高級プログラム設計(第二版)」で述べた観点は、この点とは正反対ですが、実例ではそれが間違っていると証明できます.これから紹介します.
 
   2、with文でvar演算子を使って変数(この変数はwith参照オブジェクトの属性)を再定義しても、この属性が書き込み可能な属性であれば、オブジェクトの属性には値が割り当てられます.
 
   3、with文を通じて、複数の属性を参照対象に追加し、各属性に値を付けることは不可能です.つまり、値を付与するのはオブジェクトが既に存在し、書き込むことができる属性だけです.
 
また冒頭の言葉を見てみましょう.
 
    with文の変数オブジェクトは読み取り専用ですので、結果urlは関数実行環境の一部となります.関数としての値を返します.
 
    逆に、with文の変数オブジェクトが書き込み可能であれば、先ほど3点目に触れましたが、対象に本来存在しない属性を書き込むことはできません.まずこのように理解してください.以下には別の意味があります.
 
じゃスコープの延長はどういうことですか?
 
   一般的に、「with文ブロックにおけるスコープの変数オブジェクト」は読み取り専用であるため、彼のレイヤで定義された識別子は、レイヤに格納されず、その上のスコープに格納される.ここでは「読み取り専用」という意味が分かります.
 
   Javascriptのスコープには、(スコープとして考えてみれば、関数ごとに関数名があります.匿名関数でも空関数名があります.)スコープを作成する際には、このスコープの下に本層の識別子が預けられますが、with文ブロックのスコープの「変数オブジェクト」は読み取り専用で、識別子を格納することができません.その上の階にしか保存できません.これは拡張作用分域チェーンです.実は、上記のようにオブジェクトに属性を付けることができないのと同じです.
 
   実際には、Javascriptには、ブロックレベルのスコープがないということは、関数以外に、他のブロックレベルのコードは自分のスコープがないということが完全に理解できる.
 
前に述べたwithコードブロックの変数処理方式の問題について説明します.
 
   事実をもって話す:
 
var o={href:"sssss"};
var href="1111";
function buildUrl(){
     var qs="?debug=true";     
     with(o){
          href="2222";
          var url=href+qs;
     }    
     return url;
}
var result=buildUrl();
alert(result);
alert(href);
 
    結果:2222debug=true +  1111
 
    with文では変数hrefの値は変更されておらず、oオブジェクトのhref属性が変更されていることが明らかです.
 
    つまり、withで最初に検索したのは関連するオブジェクトの属性です.ない場合は変数の値を変更します.上記の例をo対象のhref属性から削除してみてください.
 
     「オリジナル記事は、転載してください.http://lllt.iteye.comから来ました.」