JavaScript の基本的な面接の質問 (回答付き)

近年、Web フロントエンド開発に携わるプログラマが JavaScript を使用する必要が増えていますが、この記事では主に JavaScript 面接でよくある質問と回答をまとめています。

JavaScript データ型の紹介

値のタイプ (基本タイプ): 文字列、数値、ブール値、Null、未定義、シンボル (固有の値)。

参照データ型: オブジェクト、配列、関数。

注: シンボルは、一意の値を表すために ES6 で導入された新しいプリミティブ データ型です。

基本データ型と参照型のストレージの違いは何ですか?

1. 異なる保管場所:

基本的なデータ型: スタックの形式で保存され、データ自体にポイントを保存して割り当てます。typeof を使用して型を決定します。ストレージ容量は固定です。

参照型: ヒープ形式で保存され、割り当てられたオブジェクトへのポインタに保存され、instanceof を使用して型を決定します。記憶領域は固定されていません。

2. 値を渡すさまざまな方法:

基本データ型は値によって渡され、基本データ型の値は変更できません。

参照型は参照によって渡され、アプリケーション型の値は変更される可能性があります

jsの種類を確認する方法

1. タイプ

'文字列'、'数値'、'ブール'、'未定義'、'シンボル'を判定できます
が、typeof(null)を判定する場合は値が'オブジェクト'となり、配列とオブジェクトを判定する場合は両方とも'オブジェクト'になります。

2.インスタンス

原則は、コンストラクターのプロトタイプ属性がオブジェクトのプロトタイプ チェーンのどこかに現れるかどうかです。

function A() {}let a = new A();a instanceof A     //true,因为 Object.getPrototypeOf(a) === A.prototype;

3. Object.prototype.toString.call()

組み込みのブラウザ オブジェクトを判断するためによく使用され、null や未定義を含むすべての基本的なデータ型を判断できます。

Object.prototype.toString.call(null)//"[object Null]"Object.prototype.toString.call(undefined)//"[object Undefined]"Object.prototype.toString.call(Object)//"[object Function]"

4. 配列.isArray()

配列であるかどうかを判断するために使用されます。

typeof 演算子、instanceof 演算子、isPrototypeOf() メソッドの違い

typeof は、基本データ型 null、unknown、string、number、boolean、および参照データ型オブジェクト、関数などのデータの型を検出するために使用される演算子ですが、正規表現、日付、配列などの参照データ型の場合は、すべてオブジェクトとして認識されます

Instanceof は演算子でもあり、データの特定の参照タイプを簡単に識別できます。isPrototypeOf との違いは、コンストラクターのプロトタイプが指定されたオブジェクトのプロトタイプ チェーンに存在するかどうかを検出するために使用されることです。

isPrototypeOf は、指定されたオブジェクトのプロトタイプチェーンにこのメソッドを呼び出しているオブジェクトが存在するかどうかを検出するために使用されるため、本質的には検出対象が異なります。

NaNとは何ですか

NaN は Not a Number の略です。NaN 属性は、特別な非数値を参照するために使用されます。指定された属性は不正な数値ではありません。

NaN プロパティは Number.Nan プロパティと同じです。

ヒント: 値が数値かどうかを判断するには、isNaN() を使用します。その理由は、NaN はそれ自体を含め、どの値とも等しくないためです。

jsのローカルオブジェクト? 組み込みオブジェクト? ホストオブジェクト?

ネイティブ オブジェクト: ECMA-262 では、ネイティブ オブジェクトを「ホスト環境から独立した ECMAScript 実装によって提供されるオブジェクト」と定義しています。

含まれるもの:オブジェクト、関数、配列、文​​字列、ブール値、数値、日付、RegExp、エラー、EvalError、RangeError、ReferenceError、SyntaxError、TypeError、URIError。

組み込みオブジェクト: ECMA-262 では、組み込みオブジェクトを「ホスト環境とは無関係に ECMAScript 実装によって提供され、ECMAScript プログラムの実行開始時に表示されるすべてのオブジェクト」と定義しています。これは、開発者が組み込みオブジェクトを明示的にインスタンス化する必要がなく、すでにインスタンス化されているということを意味します。内容: Gobal と Math。

ホスト オブジェクト: ECMAScript によって実装されたホスト環境によって提供されるオブジェクトは、ブラウザによって提供されるオブジェクトとして理解できます。すべての BOM と DOM はホスト オブジェクトです。

スタックとヒープの違いは何ですか?

スタック: 関数パラメータ値、ローカル変数などを保存するために、コンパイラによって自動的に割り当ておよび解放されます。

ヒープ: 通常、プログラマによって割り当ておよび解放されますが、プログラマが解放しない場合は、プログラムの終了時にオペレーティング システムによって解放される場合があります。

次の変数の違いを説明してください: null、未定義、または未宣言

null は「オブジェクトがない」、つまり値が存在しないことを意味し、数値に変換すると 0 になります。一般的な使用法は次のとおりです。

(1) 関数のパラメータとしては、関数のパラメータがオブジェクトではないことを意味します。

(2) オブジェクト プロトタイプ チェーンの終点として。

unfineed は「欠損値」を意味します。つまり、ここに値があるはずですが定義されておらず、数値に変換すると NaN になります。一般的な使用法は次のとおりです。

(1) 変数が宣言されていても値が割り当てられていない場合、その変数は未定義と同じになります。

(2) 関数呼び出し時に、提供されるべきパラメータが提供されず、パラメータが未定義に等しい。

(3) オブジェクトには属性が割り当てられておらず、この属性の値は未定義です。

(4) 関数が値を返さない場合は、デフォルトで未定義を返します。

undeclared: js 構文エラー、宣言なしで直接使用、js は対応するコンテキストを見つけることができません。

for..in と object.keys の違い

Object.keys は継承されたプロトタイプのプロパティを走査しません

for...in は、継承されたプロトタイプのプロパティを反復処理します。

JSの匿名関数とは何ですか?

匿名関数: 次のような関数名のない関数です。

(function(x, y){
   
       alert(x + y);  })(2, 3);

ここ (最初の括弧内) で匿名関数が作成され、2 番目の括弧を使用して匿名関数を呼び出し、パラメーターを渡します。

JSでの関数ホイスティングについて解説します

宣言を先頭に移動できるようにする JS のデフォルトの動作は、ホイスティングと呼ばれます。JS で関数を作成する 2 つの方法は、関数宣言と関数式です。

関数宣言

特定のパラメータを持つ関数は関数宣言と呼ばれ、JS で変数を作成することは宣言と呼ばれます。のように:

hoisted(); // logs "foo"function hoisted() {
   
     console.log('foo');}

関数式

式を使用して関数を作成する場合、それは関数式と呼ばれます。例:

notHoisted(); // TypeError: notHoisted is not a functionvar notHoisted = function() {
   
      console.log('bar');};

Js の暗黙的変換の概要

jsでは演算子を動作させる際、両辺のデータが統一されていないとCPUが計算できませんが、この時コンパイラが演算子の両辺のデータを同じデータ型に自動変換して計算します。 。

这种无需程序员手动转换,而由编译器自动转换的方式就称为隐式转换

例如1 > "0"这行代码在js中并不会报错,编译器在运算符时会先把右边的"0"转成数字0`然后在比较大小

隐式转换规则:

1. 转成string类型: +(字符串连接符) 2..转成number类型:++/--(自增自减运算符) + - * / %(算术运算符) > < >= <= == != === !=== (关系运算符)

2. 转成boolean类型:!(逻辑非运算符)

例子:​​​​​

console.log([] == []) // falseconsole.log([] == ![]) // trueconsole.log([] !== [])  // trueconsole.log(NaN != NaN) // trueconsole.log(null == undefined) // trueconsole.log(null === undefined) // falseconsole.log(1 == true) // trueconsole.log(null > 0) // falseconsole.log(true + 1) // 2console.log(undefined + 1) // NaNconsole.log({} + 1) // [object Object]1console.log([] + {}) // [object Object]console.log([2,3] + [1,2])  // 2,31,2

Object.is()与原来的比较操作符"==="、"==” 的区别?

(1)两等号判等,会在比较时进行类型转换;

(2)三等号判等(判断严格),比较时不进行隐式类型转换,(类 型不同则会返回false);

(3)Object.is 在三等号判等的基础上特别处理了NaN、-0和+0,保证-0和+0不再相同,但Object.is(NaN, NaN)会返回true。Object.is应被认为有其特殊的用途,而不能用它认为它比其它的相等对比更宽松或严格。

JS 中 == 和 === 区别是什么?

1、对于string,number等基础类型,==和===有区别

1)不同类型间比较,==之比较“转化成同一类型后的值”看“值”是否相等,===如果类型不同,其结果就是不等。
2)同类型比较,直接进行“值”比较,两者结果一样。

2、对于Array,Object等高级类型,==和===没有区别

进行“指针地址”比较。

3、基础类型与高级类型,==和===有区别

1)对于==,将高级转化为基础类型,进行“值”比较。
2)因为类型不同,===结果为false。

ES5 和 ES6 分别几种方式声明变量

ES5 有俩种:var 和 function

ES6 には 6 つのタイプがあります。さらに 4 つ、let、const、class、import です。

注: let、const、および class によって宣言されたグローバル変数は、グローバル オブジェクトのプロパティにリンクされなくなります。

イベントプロキシ/イベント委任とは何ですか?

イベント プロキシ/イベント委任は、イベント バブリングの機能を使用して、複数の要素にバインドされる必要があるイベントをその祖先要素にバインドします。特に子要素を動的に追加する場合、プログラムのパフォーマンスを向上させ、メモリ領域を削減するのに非常に便利です。

イベントバブリングとは何ですか? イベントキャプチャとは何ですか?

バブリング イベント: イベントは、最も具体的なイベント ターゲットから最も具体性の低いイベント ターゲット (ドキュメント オブジェクト) までの順序でトリガーされます。

キャプチャ タイプのイベント: イベントは、最も精度の低いオブジェクト (ドキュメント オブジェクト) から開始され、次に最も正確なオブジェクトにトリガーされます (イベントはウィンドウ レベルでキャプチャすることもできますが、開発者が明確に指定する必要があります)。

イベントを追加するときは、addEventListener(event,fn,useCapture) メソッドを使用します。ベースの 3 番目のパラメーター useCapture はブール値で、イベントがキャプチャされたときに実行されるか、イベントがバブルアップしたときに実行されるかを設定するために使用されます。

注: IE ブラウザは、attachEvent() メソッドを使用します。このメソッドには関連する設定はありません。ただし、IE のイベント モデルは、デフォルトでイベントがバブルアップするとき、つまり useCapture が false に等しいときに実行されるため、useCapture は、 false に設定する方が安全であり、ブラウザーとの互換性も確保されます。

イベントの勃発を止めるにはどうすればよいでしょうか?

w3c メソッドは e.stopPropagation() で、IE は e.cancelBubble = true を使用します。例:

window.event.cancelBubble = true;e.stopPropagation();

false を返すとバブリングを防ぐこともできます。

デフォルトイベントを防ぐにはどうすればよいですか?

w3c メソッドは e.preventDefault() で、IE は次のように e.returnValue = false を使用します。

function stopDefault( e ) {  if ( e && e.preventDefault )            e.preventDefault(); //IE中阻止函数器默认动作的方式   else             window.event.returnValue = false; }

false を返すと、デフォルトの動作を防ぐこともできます。 

DOM イベントの段階は何ですか? イベント会社の理解について話しましょう

キャプチャステージ - ターゲットステージ - バブリングステージの3つのステージに分かれています

イベントプロキシを簡単に言うと、イベントは要素に直接バインドされるのではなく、その要素の親要素にバインドされ、イベントがトリガーされると(「クリック」など)、条件が判断されてイベントが実行されます。イベントがトリガーされた後。ステートメント (例: 'alert(e.target.innerhtml)')

利点: (1) コードをより簡潔にする; (2) メモリのオーバーヘッドを節約する

ネイティブ JS を使用して 2 つの onclick イベントをボタンにバインドするにはどうすればよいですか?

addEventListener を使用して複数のイベントをバインドします。たとえば

var btn = document.getElementById('btn')btn.addEventListener('click', fn1)btn.addEventListener('click', fn2)function fn1 () {
   
     console.log('我是方法1')  }function fn2 () {
   
     console.log('我是方法2')  }

応答イベントとは何ですか?

onclick マウスがオブジェクトをクリックする、onfocus がフォーカスを取得する、onblur がフォーカスを失う、onmousedown マウスが押されるなど。一般的に使用されるものは次のとおりです。

  1. マウスクリックイベント(onclick)

  2. マウスオーバーイベント (onmouseover)

  3. マウス移動イベント (onmouseout)

  4. カーソルフォーカスイベント(onfocus)

  5. 焦点が合っていないイベント ( onblur )

  6. コンテンツ選択イベント ( onselect )

  7. テキスト ボックスの内容変更イベント (onchange)

  8. イベントのロード ( onload )

  9. アンロードイベント (onunload)

閉鎖の概念?長所と短所?使われるシーンは?

クロージャの概念: クロージャは、他の関数の内部変数を読み取ることができる関数です。

  1. グローバル変数の汚染を避ける

  2. 変数をメモリ上に長期保存したい(キャッシュ変数)

欠点:

  1. メモリリーク(消費)

  2. メモリが常駐し、メモリ使用量が増加します

使用シナリオ: 関数をカプセル化するとき (プライベート プロパティとメソッドを使用する必要がある)、関数のアンチシェイク、関数のスロットリング、関数のカリー化、および要素の擬似配列へのイベントの追加では、要素のインデックス値を使用する必要があります。

メモリリークの原因

  1. 予期しないグローバル変数 (関数内で var を使用して宣言されていない変数)

  2. コンソール.ログ

  3. 閉鎖

  4. オブジェクトの循環参照

  5. 未クリアのタイマー

  6. DOM リーク (DOM ノードを取得した後、DOM ノードを削除しますが、手動で変数を解放しないと、変数内で対応する DOM ノードに引き続きアクセスできるため、リークが発生します)

新しいオペレーターは具体的に何をするのですか?

1) 空のオブジェクトを作成します。this 変数はそのオブジェクトを参照し、関数のプロトタイプも継承します。

2) this によって参照されるオブジェクトにプロパティとメソッドが追加されます。

3) 新しく作成されたオブジェクトは this によって参照され、最後に暗黙的に this が返されます。

JavaScript での this のポインタ

これは常に、関数が作成されたオブジェクトではなく、関数が実行されているオブジェクトを指します。

通常の関数呼び出しの場合、これは関数を呼び出す人です。

コンストラクターに関しては、new 演算子を使用せずに直接呼び出された場合、これはウィンドウを指します。new 演算子を使用してオブジェクト インスタンスを生成した後、これは新しく生成されたオブジェクトを指します。

無名関数、またはどのオブジェクトにも存在しない関数はウィンドウを指します。

call、apply などの場合は、指定された人が対象となります。

これについての理解を話しましょう

1) これは常に関数の直接呼び出し元 (間接呼び出し元ではない) を指します。

2) new キーワードがある場合、これは new から出てくるオブジェクトを指します。

3) イベントでは、this はターゲット要素を指しますが、特別なことは、IE のattachEvent の this は常にグローバル オブジェクト ウィンドウを指すことです。

evalは何をするのですか?

その機能は、対応する文字列を JS コードに解析して実行することです。安全ではなく、非常にパフォーマンスを消費する eval の使用は避けるべきです (JS ステートメントへの解析に 1 回、実行に 1 回の計 2 回)。

呼び出し、適用、バインドの違い

call apply binding は、関数呼び出しの this ポインターを変更できます。​​​​​​​

函数.call(对象,arg1,arg2....)函数.apply(对象,[arg1,arg2,...])var ss=函数.bind(对象,arg1,arg2,....)

1. 第一引数で関数内の this のポイント(関数が実行されるスコープ)を指定し、指定されたスコープに従って関数を呼び出します。

2. 関数を呼び出すときにパラメータを渡すことができます。call メソッドと binding メソッドは直接渡す必要がありますが、apply メソッドは配列の形式で渡す必要があります。

3. call メソッドと apply メソッドは呼び出し直後に関数を実行しますが、bind メソッドはすぐには実行されないため、関数を再度実行する必要があります。

4. このオブジェクトのポインティングを変更する際の問題は、call、apply、bind メソッドだけでなく、その変数を使用して this のポインティングを修正できることでもあります。

JavaScript スコープ チェーン

スコープ チェーンの原理はプロトタイプ チェーンと非常に似ており、変数が独自のスコープ内にない場合は、最上位まで親を探します。

注: JS にはブロックレベルのスコープがありません。ブロックレベルのスコープを形成するには、(function(){})(); を通じて即時実行の形式で実装できます。

JavaScript プロトタイプ チェーン

まず、次の 3 つの概念を理解します。

  • プロトタイプ: プロトタイプ オブジェクト。各関数にはプロトタイプ属性があります。新しいコマンドを使用してオブジェクトをインスタンス化すると、この属性がインスタンスのプロトタイプ オブジェクトになります。

  • コンストラクター: コンストラクター。プロトタイプオブジェクトを指すコンストラクター

  • __proto__: インスタンス オブジェクトのプロトタイプ

JavaScript では、インスタンス オブジェクトとプロトタイプ間のリンクをプロトタイプ チェーンと呼びます。Javascript 解析エンジンは、オブジェクト プロパティの値を読み取ると、プロトタイプ チェーンに沿って上方向に検索します。最後に見つからなかった場合、プロパティ値は未定義です。最終的にプロパティ値が見つかった場合は、結果が返されます。

継承(6つの方法)とメリット・デメリット

1. プロトタイプチェーンの継承

2. コンストラクターの継承

3. 結合継承(プロトタイプチェーン継承+コンストラクタ継承)

4. プロトタイプの継承

5. 寄生継承

6. 組み合わせ寄生継承

コード例:

//借助构造函数实现继承:缺点是父构造函数的原型链继承不了,若要全部继承除非将所有属性和方法定义在构造函数中function Parent1 () {
   
     this.name = 'parent1';}function Child1 () {
   
     //这么做的好处是定义在父构造函数中的引用类型的属性,对于子构造函数的每个实例来说是独立的  //并且在子构造函数实例化时,可以给父构造函数传参  Parent.call(this);  this.type = 'child1';}
//借助原型链实现继承:缺点是继承的引用类型属性是共享的,子构造函数的实例更改会影响其他实例上的这个属性,比如 play 属性function Parent2 () {
   
     this.name = 'parent2';  this.play = [1, 2, 3];}function Child2 () {
   
     this.type = 'Child2';}Child2.prototype = new Parent2();
//组合方式:缺点是会执行两次父构造函数function Child3 () {
   
     //执行第一次  Parent2.call(this);  this.type = 'Child3';}Child3.prototype = new Parent2(); //执行第二次
//组合优化1,不需要再将定义在父构造函数中的属性和方法再继承一次,只需要继承原型链上的Child3.prototype = Parent2.prototype;//缺点是无法区分一个实例是子函构造函数实例化的还是父构造函数实例化的let s1 = new Child3();//s1.constructor 指向了 Parent2,而不是 Child3,因为 Child3 原型对象的属性 constructor 继承了 Parent2 原型对象上的//如果你强行执行 Child3.prototype.constructor = Child3 的话,也会将 Parent2.prototype.constructor 改成 Child3
//组合优化2,通过 Object.create() 创建一个中间对象,将两个原型对象区别开来,并且继承父构造函数的原型链Child3.prototype = Object.create(Parent2.prototype);Child3.prototype.constructor = Child3;//即 Child3.prototype.__proto__ === Parent2.prototype 为 true//如此 Child3.prototype 和 Parent2.prototype 被隔离开,是两个对象,不会相互影响//这种方式为理想继承方式

変数宣言のホイスティングについて説明してください

var で宣言された変数はスコープの先頭に昇格されます。変数だけでなく関数宣言もホイストされます。

変数と関数宣言の両方のホイスティングが同じスコープ内で発生する場合でも、変数は関数よりも前に置かれます。

関数宣言と関数式の違いは何ですか?

Javascript では、パーサーが実行環境にデータをロードするときに、関数宣言と関数式は同等に扱われません。パーサーは、コードを実行する前に、まず関数宣言を読み取り、使用可能 (アクセス可能) にします。関数式に関しては、実際に解析して実行する前に、パーサーがそのコード行に到達するまで待つ必要があります。

ウィンドウ オブジェクトとは何ですか? ドキュメント オブジェクトとは何ですか?

window オブジェクトは、ブラウザーで開かれたウィンドウを表します。document オブジェクトは html ドキュメント全体を表します。実際、ドキュメント オブジェクトはウィンドウ オブジェクトのプロパティです。

document.onload イベントと document.ready イベントの違い

ページが読み込まれるときのイベントは 2 つあり、1 つは文書構造が読み込まれたことを示す準備完了 (画像などの非テキスト メディア ファイルを除く)、もう 1 つは画像を含むページのすべての要素が読み込まれたことを示す onload です。および他のファイルがロードされました。

Jsの浅いコピーと深いコピー

浅いコピーでは、オブジェクトへのポインタのみがコピーされ、オブジェクト自体はコピーされません。古いオブジェクトと新しいオブジェクトは依然として同じメモリを共有します。ただし、ディープ コピーでは同一のオブジェクトが作成され、新しいオブジェクトは元のオブジェクトとメモリを共有せず、新しいオブジェクトを変更しても元のオブジェクトは変更されません。

浅いコピー

// 第一层为深拷贝
Object.assign()
Array.prototype.slice()
扩展运算符 ...

ディープコピー

JSON.parse(JSON.stringify())

再帰関数

function cloneObject(obj) {
  var newObj = {} //如果不是引用类型,直接返回
  if (typeof obj !== 'object') {
    return obj
  }
  //如果是引用类型,遍历属性
  else {
    for (var attr in obj) {
      //如果某个属性还是引用类型,递归调用
      newObj[attr] = cloneObject(obj[attr])
    }
  }
  return newObj
}

JavaScript の引数とは正確には何ですか?

Javascript China の各関数には、関数の実際のパラメータを参照する Arguments オブジェクト インスタンスの引数があります。配列添字 "[]" を使用して引数の要素を参照できます。argument.length は関数の実際のパラメータの数であり、arguments.callee は関数自体を参照します。
関数コードでは、特別なオブジェクト引数を使用することで、開発者はパラメータ名を明示的に指定する必要がなく、添え字を使用して対応するパラメータにアクセスできます。

function test() { 
 var s = ""; 
 for (var i = 0; i < arguments.length; i++) { 
  alert(arguments[i]);             
  s += arguments[i] + ","; 
 }
 return s; 
} 
test("name", "age");//name,age 

引数にはいくつかの配列プロパティがありますが、それは実際の配列ではなく、配列のようなオブジェクトです。配列のメソッドはあまりなく、実際の配列のように .jion()、.concat()、.pop() などのメソッドを呼び出すことはできません。

「use strict」とは何ですか?これを使用する利点と欠点は何ですか?

コード内に「use strict」; という表現が出現することは、コードが strict モードに従って解析され、JavaScript がより厳密な条件で実行されることを意味します。

利点:

  • Javascript 構文の不合理で不正確な部分を削除し、奇妙な動作を軽減します。

  • コード操作のいくつかの安全でない側面を排除し、コード操作の安全性を確保します。

  • コンパイラの効率を向上させ、実行速度を向上させます。

  • 将来の Javascript の新しいバージョンへの道を開きます。

危害:

  • 「厳密モード」では、同じコードでも実行結果が異なる場合があります。

  • 「通常モード」で実行できる一部のステートメントは、「厳密モード」では実行できません。

クロスドメインとは何ですか? クロスドメインによって引き起こされる問題を解決する方法はありますか?

クロスドメインは、ブラウザの同一オリジン ポリシーに基づいて理解する必要があります。同一オリジン ポリシーとは、リクエストが同じポート、同じプロトコル、同じドメイン名に対して行われ、異なるソースからのクライアント スクリプトは読み取れないことを意味します。明示的な承認。お互いのリソースを書き込みます。
ブラウザの同一生成元ポリシーの影響を受け、同じ生成元からではないスクリプトは、他のソースからのオブジェクトを操作できません。別のソースからオブジェクトを操作したい場合は、クロスドメインを実行する必要があります。

一般的な解決策:

  • クロスオリジンリソース共有 (CORS)

  • nginxプロキシクロスドメイン

  • nodejsミドルウェアプロキシクロスドメイン

  • jsonpクロスドメイン

Json とは何かを説明する

(1)JSON は軽量のデータ交換フォーマットです。

(2) JSON は言語やプラットフォームに依存せず、JSON パーサーと JSON ライブラリはさまざまなプログラミング言語をサポートします。

(3) JSONの構文は、単純な値(文字列、数値、ブール値、null)、配列、オブジェクトの3種類の値を表現します

jsonpの原理とそれが本物のajaxではない理由を説明する

Json はスクリプト タグとコールバック関数を動的に作成することによって実装されますが、Ajax はページ更新リクエストを必要としないデータ操作です。

ネイティブ Js の実装:

(function (window,document) {
    "use strict";
    var jsonp = function (url,data,callback) {
        // 1.将传入的data数据转化为url字符串形式
        // {id:1,name:'fly63'} => id=1&name=fly63
        var dataString = url.indexof('?') == -1? '?': '&';
        for(var key in data){
            dataString += key + '=' + data[key] + '&';
        };
        // 2 处理url中的回调函数
        // cbFuncName回调函数的名字 :my_json_cb_名字的前缀 + 随机数(把小数点去掉)
        var cbFuncName = 'my_json_cb_' + Math.random().toString().replace('.','');
        dataString += 'callback=' + cbFuncName;
        // 3.创建一个script标签并插入到页面中
        var scriptEle = document.createElement('script');
        scriptEle.src = url + dataString;
        // 4.挂载回调函数
        window[cbFuncName] = function (data) {
            callback(data);
            // 处理完回调函数的数据之后,删除jsonp的script标签
            document.body.removeChild(scriptEle);
        }
        // 5.append到页面中
        document.body.appendChild(scriptEle);
    }
    window.$jsonp = jsonp;// 因为jsonp是一个私有函数外部不能调用,所有jsonp函数作文window对象的一个方法,供外部调用
})(window,document)

Cookie の欠点について話しましょうか?

(1) Cookie の数と長さの制限。各ドメインには最大 20 個の Cookie のみを含めることができ、各 Cookie の長さは 4KB を超えることはできません。4KB を超えると切り捨てられます。

(2) 安全上の問題。Cookie が誰かに傍受された場合、その人はすべてのセッション情報を取得できます。暗号化も役に立ちません。傍受者は Cookie の意味を知る必要がないため、Cookie をそのまま転送するだけで目的を達成できます。

(3) 一部の状態はクライアントに保存できません。たとえば、フォームの重複送信を防ぐには、サーバー側にカウンターを保存する必要があります。このカウンタをクライアント側に保存しても、効果はありません。

Cookie の分離とは何ですか? (または: リソースをリクエストするときに Cookie を持ち込まない方法)

複数の非プライマリ ドメイン名を使用して静的ファイルをリクエストし、静的ファイルがプライマリ ドメイン名の下に配置されている場合、静的ファイル リクエストに含まれる Cookie データをサーバーに送信するのは非常に無駄であり、分離することをお勧めします。彼ら。Cookie にはドメイン制限があるため、ドメインを越えてリクエストを送信することはできません。したがって、プライマリ以外のドメイン名を使用する場合、リクエスト ヘッダーには Cookie データが含まれません。これにより、リクエスト ヘッダーのサイズが削減され、リクエスト時間が短縮されるため、全体的なリクエストの削減、遅延の目的。同時に、この方法では Cookie がサーバーに渡されませんが、サーバーによる Cookie の処理と分析が軽減され、サーバーの http リクエストの解析速度が向上します。

Cookie、sessionStorage、localStorage の違いについて説明してください。

sessionStorage和localStorage是HTML5 Web Storage API提供的,可以方便的在web请求之间保存数据。有了本地数据,就可以避免数据在浏览器和服务器间不必要地来回传递。sessionStorage、localStorage、cookie都是在浏览器端存储的数据,其中sessionStorage的概念很特别,引入了一个“浏览器窗口”的概念。sessionStorage是在同源的同窗口(或tab)中,始终存在的数据。也就是说只要这个浏览器窗口没有关闭,即使刷新页面或进入同源另一页面,数据仍然存在。关闭窗口后,sessionStorage即被销毁。同时“独立”打开的不同窗口,即使是同一页面,sessionStorage对象也是不同的cookies会发送到服务器端。其余两个不会。Microsoft指出InternetExplorer8增加cookie限制为每个域名50个,但IE7似乎也允许每个域名50个cookie。

  • Firefox每个域名cookie限制为50个。

  • Opera每个域名cookie限制为30个。

  • Firefox和Safari允许cookie多达4097个字节,包括名(name)、值(value)和等号。

  • Opera允许cookie多达4096个字节,包括:名(name)、值(value)和等号。

  • InternetExplorer允许cookie多达4095个字节,包括:名(name)、值(value)和等号。

 

localstorage不能手动删除的时候,什么时候过期

除非被清除,否则永久保存 clear()可清楚

sessionStorage 仅在当前会话下有效,关闭页面或浏览器后被清除

 

什么是函数柯里化

函数柯里化是把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数而且返回结果的新函数的技术。

柯里化的目的是,减少代码冗余,以及增加代码的可读性。下面看一个与柯里化有关的经典例子:

// 实现一个add方法,使计算结果能够满足类似如下的预期:
// add(1)(2)(3) = 6;
// add(1, 2, 3)(4) = 10;
// add(1)(2)(3)(4)(5) = 15;
var add_currying=function(...rest){
  var sum=0;
  for(let item of rest){
   sum+=item;
  }
  var add_back = (...rest) => {
    for(let item of rest){
      sum+=item;
    }
    return add_back;
 };
 add_back.toString = () => sum;
 return add_back;
}
console.log(add_currying(1,2,3)); //6
console.log(add_currying(1,2)(3,4)); //10
console.log(add_currying(1,2)(3)(4,5)); //15
console.log(add_currying(1)(2)(3)(4)(5)(6)); //21
//打印出来会自动使用toString,即使是写var a=add_currying(1,2,3)也会自动调用此方法(默认将函数语句以字符串打出)
//而为了打印出我们想要的结果我们就需要自己重写toString方法
//如果不用es6的三点运算符就只能使用以前的Array.prototype.slice.call(arguments)方法

js如何处理防抖和节流?

ウィンドウのサイズ変更、スクロール、入力ボックスの内容の確認などの操作を実行するときに、イベント処理関数の呼び出し頻度が無制限だと、ブラウザーの負担が増大し、ユーザー エクスペリエンスが非常に低下します。
現時点では、デバウンス (アンチシェイク) とスロットル (スロットル) を使用して、実際の効果に影響を与えることなく呼び出し頻度を減らすことができます。

関数デバウンス:

イベントが連続して発生した場合、一定時間内に再度イベントが発生しなかった場合、イベント処理機能は 1 回だけ実行され、設定時間前に再度イベントが発生すると遅延が再開されます。
以下に示すように、スクロール イベントが連続してトリガーされた場合、ハンドル関数は実行されず、スクロール イベントが 1000 ミリ秒以内にトリガーされなかった場合は、遅延してスクロール イベントがトリガーされます。

function debounce(fn, wait) { 
 var timeout = null; 
 return function() { 
  if(timeout !== null) clearTimeout(timeout);           
  timeout = setTimeout(fn, wait); 
 } 
} 
// 处理函数 
function handle() {      
 console.log(Math.random()); 
} 
// 滚动事件
window.addEventListener('scroll', debounce(handle, 1000)); 函数节流

機能のスロットル:

イベントが継続的にトリガーされる場合、イベント処理関数は一定期間内に 1 回だけ呼び出されることが保証されます。
絞りについての一般的な説明は、蛇口に水を入れるときのようなものです。バルブが開くと、水が流れ落ちます。勤勉と倹約という伝統的な美徳を守り、蛇口を絞らなければなりません。回すのが最善です。私たちの意図と一定のルールに従って蛇口を小さくし、時間内に一滴ずつ滴下します。
以下に示すように、スクロール イベントが連続してトリガーされた場合、ハンドル関数はすぐには実行されず、1000 ミリ秒ごとに実行されます。​​​​​​​

var throttle =function(func, delay) {  var prev = Date.now();  return function() {   var context = this;  var args = arguments;   var now = Date.now();   if (now - prev >= delay) {    func.apply(context, args);                              prev = Date.now();  }  } }function handle() {               console.log(Math.random()); }         window.addEventListener('scroll', throttle(handle, 1000)); 

JS のガベージ コレクション メカニズムとは何ですか?一般的に使用されるものはどれですか?また、それはどのように処理されますか?

JS のガベージ コレクション メカニズムは、メモリ リークを防ぐことです。メモリ リークの意味は、特定のメモリが必要なくなってもまだ存在していることです。ガベージ コレクション メカニズムは、断続的かつ不定期に使用されなくなった変数を見つけることです。そして、それらが指すメモリを解放します。
JS での最も一般的なガベージ コレクション方法は、マーク アンド スイープです。
動作原理: 変数が環境に入ると、その変数は「環境に入った」とマークされます。変数が環境から離れると、「環境から離れる」とマークされます。「環境から離れる」とマークされたメモリはリサイクルされます。

作業過程:

  1. ガベージ コレクターは、実行時にメモリに格納されているすべての変数にマークを付けます。

  2. 環境内の変数、および環境内の変数によって参照される変数のタグを削除します。

  3. 再度マークされた変数は、削除される変数とみなされます。

  4. ガベージ コレクターはメモリのクリーンアップ作業を完了し、マークされた値を破棄し、それらの値が占有しているメモリ領域を再利用します。

これらの操作はメモリ リークを引き起こす可能性があります

グローバル変数、クロージャ、DOM がクリアまたは削除されても、イベントはクリアされず、子要素には参照が含まれます。

仮想DOMとは

ドキュメント オブジェクト モデル (DOM) は、JavaScript などの言語が HTML ドキュメントにアクセスして操作できるようにするインターフェイスを定義します。要素はツリー内のノードによって表され、インターフェイスを使用して要素を操作できます。ただし、このインターフェイスにはコストがかかり、非常に頻繁に多数の DOM 操作が行われるとページの速度が低下する可能性があります。

Vue は、メモリ内にドキュメント構造の仮想表現を実装することでこの問題を解決します。仮想ノード (VNode) は DOM ツリー内のノードを表します。操作が必要な場合は、実際の DOM ではなく仮想 DOM のメモリ内で計算と操作を実行できます。これは当然高速であり、仮想 DOM アルゴリズムが実際の DOM 構造を更新するための最も最適化された方法を計算できるようになります。

計算されると、実際の DOM ツリーに適用されてパフォーマンスが向上します。そのため、vue や React などの仮想 DOM ベースのフレームワークが非常に注目されています。

Ajaxの使用

いわゆる非同期とは、サーバーにリクエストを送信するときに、結果を待つ必要がなく、同時に他のことを行うことができ、結果が利用可能になると、設定に従って後続の操作を実行することを意味します。同時に、ページは全ページではなくなり、ユーザー エクスペリエンスが更新され、向上しました。
Ajaxの作成手順:
1) XMLHttpRequestオブジェクト(非同期呼び出しオブジェクト)を作成します。

var xhr = new XMLHttpRequest();

2) 新しい HTTP リクエスト (メソッド、URL、非同期かどうか) を作成します。

xhr.open(‘get’,’example.php’,false);

3) HTTPリクエストの状態変化に応答する機能を設定します。
onreadystatechange イベントの readyState 属性は 4 に等しくなります。応答の HTTP ステータスは 200 (OK) または 304 (未変更) です。
4) httpリクエストを送信する

xhr.send(data);

5) 非同期呼び出しによって返されたデータを取得します
注:
1) ページが初めてロードされるときは、関連するすべてのデータを一度に Web サーバーに出力するようにしてください。ページがロードされた後でのみ、ユーザーは ajax を使用します操作時に対話します。
2) 同期 ajax により、IE でページがフリーズします。したがって、非同期 ajax を使用することをお勧めします。
3) Ajax リクエストの数を最小限に抑える
4) Ajax セキュリティの問題 クライアント側でのフィルタリングを避けるために、機密データはサーバー側で処理する必要があります。主要なビジネス ロジック コードもサーバー側で処理する必要があります。

Ajax ネイティブの書き込みメソッド

function ajax() {
	//创建一个 XHR 对象
	let oAjax = window.XMLHttpRequest ? (new XMLHttpRequest()) : (new window.ActiveXobject('Microsoft.XMLHTTP'));
	//返回一个函数,这是函数柯里化操作,不用每次调用 ajax 都判断浏览器环境
	//但是会占用更多的内存,因为总是会保存外部函数的作用域
	return function(url, fnSucc, fnFaild) {
		//只要 XHR 对象的 readyState 属性的值发生改变,就触发这个事件
		oAjax.onreadystatechange = function() {
			// readyState 属性是 0-4 的值,当为 4 时,表示已经接收到全部响应数据,并可以在客户端使用
			if (oAjax.readyState === 4) {
				//响应的 HTTP 状态
				let s = oAjax.status;
				if (s === 200 || s === 206 || s === 304) {
					//将响应主体被返回的文本作为参数传给这个函数,并执行这个函数
					if (fnSucc) fnSucc(oAjax.responseText);
				} else {
					if (fnFaild) fnFaild(oAjax.status);
				}
			}
		};
		//启动一个请求,准备发送
		oAjax.open('GET', url, true);
		//发送请求
		oAjax.send(null);
	}
}

Ajaxリクエストを行う際のgetメソッドとpostメソッドの違い

最も直感的な違いは、GET では URL にパラメータが含まれるのに対し、POST ではリクエスト本文を通じてパラメータが渡されることです。

  • GET はブラウザーがロールバックしても無害ですが、POST はリクエストを再度送信します。

  • GET で生成された URL アドレスはブックマークできますが、POST ではブックマークできません。

  • GET リクエストはブラウザによってアクティブにキャッシュされますが、POST は手動で設定しない限りキャッシュされません。

  • GET リクエストは URL エンコードのみ可能ですが、POST は複数のエンコード方法をサポートしています。

  • GET リクエストのパラメータはブラウザ履歴に完全に保持されますが、POST のパラメータは保持されません。

  • GET リクエストの URL で送信されるパラメータには長さの制限がありますが、POST リクエストの長さには制限がありません。

  • パラメータのデータ型に関しては、GET は ASCII 文字のみを受け入れますが、POST には制限がありません。

  • GET はパラメータが URL 上で直接公開されるため、POST よりも安全性が低く、機密情報を渡すために使用することはできません。

  • GET パラメータは URL 経由で渡され、POST はリクエスト本文に配置されます。

Javascript では、実行中にオブジェクトを検索するときに、プロトタイプ関数は検索されません。

Object.hasOwnProperty(proName): オブジェクトに指定した名前のプロパティがあるかどうかを判断するために使用されます。ただし、このメソッドでは、オブジェクトがプロトタイプ チェーンにプロパティを持っているかどうかを確認できないことに注意してください。プロパティはオブジェクト自体のメンバーである必要があります。

JSを遅延ロードするにはどのような方法がありますか?

JS の遅延読み込みは、ページの読み込み速度の向上に役立ちます。

遅延と非同期、DOM の動的作成 (最も一般的に使用される)、オンデマンドでの JS の非同期ロード

defer: 遅延スクリプト。すぐにダウンロードしますが、実行を遅らせて (実行前にページ全体が解析されるまで遅らせます)、スクリプトを表示された順序で実行します。
async: 非同期スクリプト。ダウンロード後すぐに実行されますが、スクリプトの出現順に実行されるとは限りません。

同期と非同期の違いは何ですか?

同期の概念はオペレーティング システムにあります。さまざまなプロセスが連携して特定のタスクを完了し、順序が調整されます (ブロック、ウェイクアップなどを通じて)。同期では、誰が最初で誰が最後になるかという順序が重視されます。非同期には順序性がありません。

同期: ブラウザがサーバーにアクセスし、ユーザーはページが更新されていることを確認し、リクエストを再送信します。リクエストが完了すると、ページが更新され、新しいコンテンツが表示され、ユーザーは新しいコンテンツを確認して次のステップに進みます。
非同期: ブラウザーがサーバー リクエストにアクセスし、ユーザーは通常どおりに動作し、ブラウザーがバックエンドでリクエストを作成します。リクエストが完了すると、ページは更新されず、新しいコンテンツが表示され、ユーザーには新しいコンテンツが表示されます。

ページのエンコーディングと要求されたリソースのエンコーディングが一致しない場合はどうすればよいですか?

リクエストされたリソースのエンコーディングがページのエンコーディング(外部 js ファイルのエンコーディングなど)と異なる場合。外部リソースのエンコード方式に応じて、charset="utf-8" または "gbk" として定義できます。

たとえば、http://www.fly63.com/a.html には http://www.fly63.com/test.js が埋め込まれています。

a.html のエンコードは gbk または gb2312 です。インポートされた js エンコーディングは utf-8 であるため、次のようにする必要があります。

<script src="http://www.fly63.com/test.js" charset="utf-8"></script>

モジュール開発を行うにはどうすればよいですか?

モジュール開発とは、複雑な問題や一連の問題を解決するときに、分類思考に従って問題を体系的に分解することを指します。

モジュール化は、複雑なシステムを、より合理的なコード構造と高い保守性を備えた管理可能なモジュールに分解する方法です。ソフトウェア業界の場合: システムは、結合性が高く結合度の低いモジュールのセットに分解されます。

(1) カプセル化されたモジュールを定義します。
(2) 他のモジュールに対する新しいモジュールの依存関係を定義します。
(3) 他のモジュールの導入をサポートします。非伝統的なモジュール開発方法の仕様が JavaScript で登場しました。CommonJSモジュール仕様、AMD(Asynchronous Module Definition)、CMD(Common Module Definition)など AMD は非同期モジュール定義であり、すべてのモジュールは非同期でロードされ、モジュールのロードは後続のステートメントの実行には影響しません。

AMD と CMD の仕様の違いは何ですか?

AMD は、RequireJS のプロモーション プロセス中のモジュール定義の標準化された出力です。CMD は、SeaJS のプロモーション プロセス中のモジュール定義の標準化された出力です。違い:

  1. 1) 依存モジュールの場合、AMD は事前に実行され、CMD は遅延して実行されます。ただし、RequireJS 2.0からは遅延実行もできるように変更されました(記述方法によって処理方法が異なります)。

  2. 2) CMD は最も近い場所への依存を促進し、AMD は前面への依存を促進します。

  3. 3) AMD の API はデフォルトで複数の目的に使用されるように設定されていますが、CMD の API は厳密に区別されており、単一の責任を主張しています。

ページのリフローと再描画について説明する

要素のサイズ、レイアウト、非表示などの変更により、レンダー ツリーの一部(またはすべて)を再構築する必要がある場合。これをリフローといいます。

各ページには、ページが初めてロードされるとき、少なくとも 1 回のリフローが必要です。レンダー ツリーを構築する必要があるため、この時点でリフローが必ず発生します。

リフロー中、ブラウザはレンダリング ツリーの影響を受けた部分を無効化し、レンダリング ツリーのこの部分を再構築します。リフローの完了後、ブラウザは影響を受けた部分を画面に再描画します。このプロセスは再描画と呼ばれます。

レンダー ツリー内の一部の要素で属性を更新する必要がある場合、これらの属性は要素の外観とスタイルにのみ影響し、背景色などのレイアウトには影響しません。それを再描画といいます。

違い:

リフローは確実に再描画を引き起こしますが、再描画は必ずしもリフローを引き起こすとは限りません。たとえば、色が変わった場合のみ再描画が発生し、リフローは発生しません。

リフローは、表示される DOM 要素の追加または削除、要素の位置の変更、要素のサイズの変更 (マージン、パディング、境界線、幅と高さ、コンテンツの変更など)、ページ レイアウトと幾何学的プロパティが変更された場合に必要です。

ブラウザのスクロール距離

表示可能領域とページの上部の間の距離

var scrollTop=document.documentElement.scrollTop||document.body.scrollTop

表示エリアのサイズ

(1)innerXXX (ieと互換性がありません)

window.innerHeight スクロール バーの幅を含むビジュアル領域の高さ
window.innerWidth スクロール バーの幅を含むビジュアル領域の幅

(2)document.documentElement.clientXXX(IE互換)

document.documentElement.clientWidth スクロール バーの幅を除く、ビジュアル領域の幅
document.documentElement.clientHeight スクロール バーの幅を除く、ビジュアル領域の高さ

ノードの種類は何種類ありますか?それは何ですか?

(1)要素ノード:nodeType ===1;

(2) テキストノード:nodeType ===3;

(3)属性ノード:nodeType ===2;

innerHTMLとouterHTMLの違い

innerHTML (要素内に含まれるコンテンツ)

innerHTML (self と要素内のコンテンツ)

document.write と innerHTML の違い

document.write はコンテンツをページに書き込み、それをクリアして元のコンテンツを置き換えます。これにより、再描画が発生します。

document.innerHTML は再描画せずにコンテンツを Dom ノードに書き込みます

offsetWidth offsetHeight と clientWidth clientHeight の違い

(1)offsetWidth (コンテンツの幅 + パディングの幅 + ボーダーの幅)
(2) offsetHeight (コンテンツの高さ + パディングの高さ + ボーダーの高さ)
(3) clientWidth (コンテンツの幅 + パディングの幅)
(4) clientHeight (コンテンツの高さ + パディングの高さ)

DOM 操作

(1) 新規ノードの作成

createDocumentFragment() //DOM フラグメントを作成します
createElement() //特定の要素を作成します
createTextNode() //テキスト ノードを作成します

(2) 追加、削除、置換、挿入

appendChild()
removeChild()
replaceChild()
insertBefore() //既存の子ノードの前に新しい子ノードを挿入します

(3) 検索

getElementsByTagName() //タグ名を通じて
getElementsByName() //要素の Name 属性の値を通じて (IE は強力なフォールト トレランスを備えているため、名前の値と等しい ID を含む配列を取得します) getElementById()
/ /要素IDを通じて、固有の性別

BOM と DOM の関係

BOM の正式名称は Browser Object Model で、主にブラウザのウィンドウとフレームを扱うブラウザ オブジェクト モデルです。

DOM の正式名称は Document Object Model で、HTML と XML のアプリケーション プログラミング インターフェイス (API) であり、W3C 標準に準拠しており、すべてのブラウザが準拠する標準です。

JSはBOM(Browser Object Model)オブジェクトにアクセスすることでクライアント(ブラウザ)へのアクセス・制御・変更を行いますが、BOMのウィンドウにはドキュメントが含まれているため、ウィンドウオブジェクトのプロパティやメソッドを直接利用・認識することができます。 window オブジェクトの document 属性を使用すると、document 属性を通じて XHTML ドキュメントのコンテンツと構造にアクセス、取得、および変更できます。ドキュメント オブジェクトは DOM のルート ノードであるためです。

BOM の中に DOM (オブジェクト) が含まれているとも言えますが、ブラウザがアクセスのために提供するのが BOM オブジェクトであり、BOM オブジェクトから DOM オブジェクトに至るまで、ブラウザやブラウザが読み込むドキュメントを js で操作することができます。

配列オブジェクトのネイティブ メソッドとは何ですか?それらをリストしてみましょう。

ポップ、プッシュ、シフト、シフト解除、スプライス、リバース、ソート、連結、結合、スライス、toString、indexOf、lastIndexOf、reduce、reduceRight、forEach、map、filter、every、some

Pop: 配列の最後の要素を削除して返します (元の配列を変更します);
Push: 加算後の配列の長さを返します (元の配列を変更します);
SHIFT: 配列の最初の要素を削除して返します (元の配列を変更します) array);
unshift : 配列の先頭に要素スライスを挿入します
: スライス (添え字、数値) は、トリミングされた配列を返します (元の配列を変更せずに);
splice: 配列の要素を挿入、削除、または置換します concat
: 配列をマージします結合した配列を返します (元の配列を変更せずに) 元の配列);
結合: 識別子を使用して配列を文字列にリンクし、結合された文字列を返します (元の配列を変更せずに);
逆: 配列を反転します (元の配列を変更します) array);
toString: 配列を文字列に変換します;
split: 文字列を分割して配列に格納します;
forEach: 主に配列を走査するために使用されます;
Every: 主に配列内の各要素が条件を満たしているかどうかを確認するために使用されます関数、いずれかが条件を満たさない場合は false を返します;
indexOf: 主に配列内の要素を検索し、要素の位置を返すために使用されます。

文字列メソッド

charAt(): 添字に基づいて対応する値を検索します。

charCodeAt(): 添字値から対応する文字 Unicode エンコーディングを検索します。

IndexOf(): 対応する添え字を文字で検索します (最初に出現)

lastIndexOf(): 文字全体に現れる最後の添字値を検索します。

lice(): インターセプト文字列、2 つのパラメータ、(開始位置、終了位置)

split(): 区切り文字に従って文字列を配列に分割します。

substring(): インターセプト文字列、(開始位置、終了位置)

substr(): 指定された位置と長さの文字列をインターセプトします (開始位置、長さ)

toLowerCase(): 文字列を小文字に変換します

toUpperCase(): 文字列を大文字に変換します

trim(): 文字列の前後のスペースをすべて削除します。

JS の Array.splice() メソッドと Array.slice() メソッドの違いは何ですか

早速、最初の例を見てみましょう。

var arr=[0,1,2,3,4,5,6,7,8,9];//设置一个数组console.log(arr.slice(2,7));//2,3,4,5,6console.log(arr.splice(2,7));//2,3,4,5,6,7,8//由此我们简单推测数量两个函数参数的意义,slice(start,end)第一个参数表示开始位置,第二个表示截取到的位置(不包含该位置)splice(start,length)第一个参数开始位置,第二个参数截取长度

次に 2 番目のものを見てください。

var x=y=[0,1,2,3,4,5,6,7,8,9]console.log(x.slice(2,5));//2,3,4console.log(x);[0,1,2,3,4,5,6,7,8,9]原数组并未改变//接下来用同样方式测试spliceconsole.log(y.splice(2,5));//2,3,4,5,6console.log(y);//[0,1,7,8,9]显示原数组中的数值被剔除掉了

スライスとスプライスはどちらも配列オブジェクトをインターセプトしますが、それらの間には明らかな違いがあります。関数パラメータのスライスとスプライスの最初のパラメータはインターセプトの開始位置であり、スライスの 2 番目のパラメータはインターセプトの終了位置です (含まれていません) ).、および splice の 2 番目のパラメーター (開始位置からのインターセプトの長さを示します)、slice は元の配列を変更せず、splice は元の配列内のインターセプトされたデータを直接削除します。

JS でオブジェクトのプロパティを動的に追加/削除するにはどうすればよいですか?

object.property_name = value を使用してオブジェクトにプロパティを追加し、delete object.property_name を使用してプロパティを削除できます。

例:

let user = new Object();// adding a propertyuser.name='Anil';user.age  =25;console.log(user);delete user.age;console.log(user);

画像の遅延ロードとプリロード

プリロード: New Image(); が一般的に使用され、src を設定してプリロードを実装し、onload メソッドを使用してプリロード完了イベントをコールバックします。​​​​​​​

function loadImage(url, callback){
   
       var img = new Image(); //创建一个Image对象,实现图片预下载    img.src = url;    if (img.complete){
   
            // 如果图片已经存在于浏览器缓存,直接调用回调函数        callback.call(img);        return; // 直接返回,不用再处理onload事件    }    img.onload = function (){
   
       //图片下载完毕时异步调用callback函数。    callback.call(img);//将回调函数的this替换为Image对象 ,如果你直接用img.width的时候,图片还没有完全下载下来    };}

遅延読み込み: 主な目的は、サーバー フロントエンドを最適化し、サーバー フロントエンドの負荷を軽減し、1 回限りのリクエストまたは遅延リクエストの数を減らすことです。実装方法:
1. 1 つ目は、setTimeOut と setInterval を使用して読み込みを遅延させる純粋な遅延読み込みです
2. 2 つ目は、特定の条件が満たされるか、特定のイベントがトリガーされた場合にのみ非同期ダウンロードを開始する条件付き読み込みです。
3. 3 番目の方法は、視覚領域をロードすることです。つまり、ユーザーに表示される領域のみをロードします。これは主にスクロール バーを監視することによって実現されます。一般に、ユーザーが表示する前に、一定の距離でロードが開始されます。画像をプルダウンすると、ユーザーが画像を確認できるようになります。

コールバックとは何ですか

コールバック関数は、パラメータまたはオプションとしてメソッドに渡される通常の JS 関数です。別の関数の実行が終了した後に実行される関数であるため、コールバックと呼ばれます。

JS では、関数はオブジェクトであるため、関数はパラメーターとして関数を受け入れることができ、他の関数によって返すことができます。

JS のホスト オブジェクトとネイティブ オブジェクトの違いは何ですか?

ホスト オブジェクト: これらは、実行環境によって提供されるオブジェクトです。これは、異なるコンテキストでは異なることを意味します。たとえば、ブラウザにはウィンドウなどのオブジェクトが含まれていますが、Node.js 環境ではノード リストなどのオブジェクトが提供されます。

ネイティブ オブジェクト: これらは JS の組み込みオブジェクトです。JS を使用する場合、組み込みオブジェクトは実行時環境の影響を受けないため、グローバル オブジェクトとも呼ばれます。

プログレッシブエンハンスメントとグレースフルデグラデーション

段階的な強化: 最も基本的な機能を確保するために低バージョンのブラウザー用のページを構築し、その後、より優れたユーザー エクスペリエンスを実現するために、高度なブラウザー用のエフェクトやインタラクションなどを改善します。

グレースフル デグラデーション: 最初から完全な機能を構築し、それから下位バージョンのブラウザーと互換性を持たせます。

Web ワーカーと Web ソケット?

websocket: 単一の永続的な接続上で全二重の双方向通信を提供します。カスタム プロトコル (ws://、wss://) を使用すると、同一生成元ポリシーは Web ソケットに適用されません。
Web ワーカー: バックグラウンドで実行され、ページのパフォーマンスに影響を与えない JavaScript。

ワーカーの作成: var worker = new Worker(url);
ワーカーにデータを送信: worker.postMessage(data);
ワーカーから返されたデータを受信: worker.onmessage
ワーカーの実行を終了: worker.terminate();

ブラウザのスレッド

JS エンジン スレッド: JS コード、ユーザー入力、ネットワーク リクエストなどを解釈して実行します。

GUI スレッド (レンダリング スレッド): ユーザー インターフェイスを描画し、JS メイン スレッドと相互排他的です。

HTTP ネットワーク リクエスト スレッド: ユーザーの GET、POST、およびその他のリクエストを処理し、戻り結果を取得した後、コールバック関数をイベント キューにプッシュします。

タイマー トリガー スレッド: setTimeout、setInterval は時間の終了を待ち、実行関数をイベント キューにプッシュします。

イベント処理スレッド: クリック、マウス、入力などの対話型イベントが発生すると、イベント処理関数がイベント キューにプッシュされます。

js実行機構、イベントループ

JavaScript 言語の主な特徴は、シングルスレッドであり、一度に 1 つのことしか実行できないことです。シングルスレッドとは、すべてのタスクをキューに入れる必要があり、前のタスクが完了するまで次のタスクは実行されないことを意味します。前のタスクに時間がかかると、次のタスクも待たされることになります。

JavaScript 言語の設計者はこの問題に気づき、すべてのタスクを同期タスク (synchronous) と非同期タスク (asynchronous) の 2 種類に分類し、すべての同期タスクが実行されるまでは、非同期タスクは実行されなくなります。実装される。

Web サイトを開くとき、Web ページのレンダリング プロセスでは、ページ スケルトンやページ要素のレンダリングなど、多くの同期タスクが実行されます。画像や音楽の読み込みなど、多くのリソースを消費し、時間がかかるタスクは非同期タスクです。

JSの非同期では、マクロタスクに出会ったら、先にマクロタスクを実行してイベントキューに入れ、次にマイクロタスクを実行してイベントキューに入れるという仕組みになっていますが、この2つのキューはは 1 つのキューではありません。

取り出すときは、まずマイクロタスクからコールバック関数を取得し、次にマクロタスクのQueueからマクロタスクのコールバック関数を取得します。

宏任务:整体代码 script,setTimeout,setInterval
微任务:Promise,process.nextTick

JS为什么要区分微任务和宏任务

(1)js是单线程的,但是分同步异步
(2)微任务和宏任务皆为异步任务,它们都属于一个队列
(3)宏任务一般是:script,setTimeout,setInterval、setImmediate
(4)微任务:原生Promise
(5)遇到微任务,先执行微任务,执行完后如果没有微任务,就执行下一个宏任务,如果有微任务,就按顺序一个一个执行微任务

减少页面加载时间的方法

  • 优化图片

  • 图像格式的选择(GIF:提供的颜色较少,可用在一些对颜色要求不高的地方)

  • 优化css(压缩合并css,如margin-top,margin-left...)

  • 网址后加斜杠(如www.campr.com/目录,会判断这个“目录是什么文件类型,或者是目录。)

  • 标明高度和宽度(如果浏览器没有找到这两个参数,它需要一边下载图片一边计算大小,如果图片很多,浏览器需要不断地调整页面。这不但影响速度,也影响浏览体验。当浏览器知道了高度和宽度参数后,即使图片暂时无法显示,页面上也会腾出图片的空位,然后继续加载后面的内容。从而加载时间快了,浏览体验也更好了。)

  • 减少http请求(合并文件,合并图片)。

线程与进程的区别

一个程序至少有一个进程,一个进程至少有一个线程。线程的划分尺度小于进程,使得多线程程序的并发性高。

另外,进程在执行过程中拥有独立的内存单元,而多个线程共享内存,从而极大地提高了程序的运行效率。

线程在执行过程中与进程还是有区别的。每个独立的线程有一个程序运行的入口、顺序执行序列和程序的出口。

但是线程不能够独立执行,必须依存在应用程序中,由应用程序提供多个线程执行控制。

論理的な観点から見ると、マルチスレッドの意味は、アプリケーション内で複数の実行部分を同時に実行できることです。ただし、オペレーティング システムは、プロセスのスケジューリング、管理、およびリソース割り当てを実装するために、複数のスレッドを複数の独立したアプリケーションとはみなしません。これがプロセスとスレッドの重要な違いです。

意味論についてのあなたの理解について教えてください。

1. スタイルが削除または失われると、ページは明確な構造を示すことができます: HTML 自体にはパフォーマンスがありません。たとえば、<h1> は太字、フォント サイズは 2em、太字、<strong> は太字、do であることがわかります。これは HTML のパフォーマンスではなく、HTML のデフォルトの CSS スタイルが機能しているのだと思います。

したがって、スタイルが削除または失われた場合、ページの明確な構造はセマンティック HTML 構造の利点ではありません。ただし、ブラウザにはデフォルトのスタイルがあります。デフォルト スタイルの目的は、HTML のセマンティクスをより適切に表現することです。ブラウザのデフォルトのスタイルとセマンティックな HTML 構造は切り離せないものであると言われています。

2. スクリーン リーダー (訪問者が視覚障害がある場合) は、マークアップに完全に基づいてページを「読み取り」ます。

3. PDA や携帯電話などのデバイスは、通常のコンピュータ ブラウザのように Web ページをレンダリングできない場合があります (通常、これらのデバイスの CSS サポートが弱いため)。

4. SEO に役立つ: 検索エンジンと良好なコミュニケーションを確立すると、クローラーがより効果的な情報をクロールできるようになります。クローラーはタグに依存して各キーワードのコンテキストと重みを判断します。

5. チームの開発と保守が容易になり、セマンティクスが読みやすくなります。これは、Web ページの次のステップにおける重要な傾向です。W3C 標準に従うチームはすべてこの標準に従うため、差別化が低下する可能性があります。

Web サイトのリソースを提供するために複数のドメイン名を使用する方が効率的であるのはなぜですか?

1. CDN キャッシュがさらに便利になりました

2. ブラウザーの同時実行制限を突破します (通常、ドメイン名ごとに確立されるリンクは 6 つまでです)

3. Cookie を使用せず、帯域幅を節約します。特にアップリンク帯域幅は一般にダウンリンク帯域幅よりも遅くなります。

4. 不要なセキュリティ問題 (メイン サイトの Cookie を盗むための js のアップロードなど) を防ぐために、UGC コンテンツをメイン サイトから分離します。このため、ユーザー コンテンツのドメイン名は、自身のメイン サイトのサブドメイン名ではなく、完全に独立したサードパーティのドメイン名でなければなりません。

5. データは分割され、さらには異なる物理クラスターに分割されるため、サブドメイン名を使用してデータを転用することが容易になります。これはあまり使われないかもしれません。

PS: Cookie の問題に関しては、帯域幅は二の次であり、セキュリティの分離が第一です。複数のドメイン名については、多ければ多いほど良いというわけではありません。サーバーは一般的な解釈を行うことができますが、ブラウザーが DNS 解釈を行うには時間がかかり、ドメイン名が多すぎます。https を使用したい場合は、まださらに証明書を購入して展開します。

コードをどのように整理して最適化しますか?

内部: モジュールモード; 外部: 継承

コードの再利用

グローバル変数 (名前空間、囲まれた空間、モジュラー mvc など) を避ける

機能の肥大化を避けるために機能を分割する

コメント

フロントエンドのモジュール化とコンポーネント化

モジュール化: 再利用可能。主に JavaScript コードの機能カプセル化に焦点を当て、コピーされた JavaScript コードを分離して整理し、特定の機能を持つモジュールにカプセル化します。

コンポーネント化: 再利用可能、UI 部分に重点が置かれています。ヘッダー、ポップアップ ボックス、確認ボタンなど、ページの各コンポーネントをコンポーネントにすることができます。各コンポーネントには独立した HTML、CSS、JS コードがあります。 。

HTTPキャッシュの仕組みと機能は?

定義: ブラウザ キャッシュは、ブラウジングを高速化するためのものです。ブラウザは、最近リクエストしたドキュメントをユーザーのディスクに保存します。訪問者がこのページを再度リクエストすると、ブラウザはローカル ディスクからドキュメントを表示できるため、ページの読み取りを高速化できます。
キャッシュの役割:
1. 遅延を軽減し、Web サイトを高速化し、ユーザー エクスペリエンスを向上させます。
2. ネットワークの輻輳を回避し、リクエスト量を減らし、出力帯域幅を減らします。
実装の意味:
Cache-Control の max-age は、コンテンツ キャッシュを実装する主な手段です。一般的な戦略は 3 つあります: max-age と Last-Modified (If-Modified-Since) の組み合わせ、max-age のみ、max-age年齢とETagの組み合わせ。

強制キャッシュの場合、サーバーはブラウザにキャッシュ時間を通知します。キャッシュ時間中、次のリクエストはキャッシュを直接使用します。時間内にない場合は、比較キャッシュ ポリシーが実行されます。
比較キャッシュでは、キャッシュ情報の Etag と Last-Modified がリクエストを通じてサーバーに送信され、サーバーによって検証され、ステータス コード 304 が返された場合、ブラウザはキャッシュを直接使用します。

一般的な HTTP ステータス コード

400 クライアント要求には構文エラーがあるため、サーバーは理解できません。
403 サーバーは要求を受信しましたが、サービスの提供を拒否します。 | 200成功し
クライアント要求は


JS の主なエラーの種類は何ですか?

JS には 3 種類のエラーがあります。

読み込み時エラー: Web ページの読み込み時に発生するエラー (構文エラーなど) は読み込み時エラーと呼ばれ、動的にエラーが生成されます。

ランタイムエラー: HTML 言語でのコマンドの誤用によって引き起こされるエラー。

ロジック エラー: これらのエラーは、異なる操作を持つ関数で間違ったロジックを実行することによって発生します。

JS のデザインパターンをいくつか列挙します。

デザイン パターンは、ソフトウェア デザインにおける一般的な問題に対する一般的な再利用可能なソリューションです。デザイン パターンのいくつかを次に示します。

作成パターン: このパターンは、オブジェクトのインスタンス化プロセスを抽象化します。

構造パターン: これらのパターンは、さまざまなクラスとオブジェクトを処理して、新しい機能を提供します。

動作モデル: パブリッシュ/サブスクライブ モデルとも呼ばれ、オブザーバーと複数のオブザーバー間の 1 対多のオブジェクト関係を定義します。

並列設計パターン: これらのパターンは、マルチスレッド プログラミング パラダイムを扱います。

建築設計パターン: これらのパターンは、建築設計を扱うために使用されます。

es6の新機能

  1. 定数にしましょう

  2. テンプレート文字列

  3. アロー関数

  4. 関数パラメータのデフォルト値

  5. オブジェクトと配列の構造化

  6. 和の…の為に…

アロー関数とは何なのか説明してください。

アロー関数は、ES6 以降で関数式を記述するための簡潔な方法です。アロー関数はコンストラクターとして使用できず、this、arguments、super または new.target キーワードをサポートしていません。これらはメソッド以外の関数に最適です。 

通常、アロー関数は const function_name = () => {} のようになります。​​​​​​

const greet=()=>{console.log('hello');}greet();

通常の関数とアロー関数の違い

1. 通常の関数は、
bind、call、apply を通じてこのポインタを変更できます。New を
使用できます
。 2. アロー関数
自体にはこのポインタはありません。
これは、
アロー関数の最初の通常関数からこれを継承する通常関数から継承されます。アロー関数のこの点が変更されると、それに応じてアロー関数のこの点も変更されます アロー関数
の外層に通常の関数がない場合、ウィンドウのこの点は定義できませんアロー関数にはコンストラクターがないため、new を使用してアロー関数を
呼び出すとエラーが報告されます。

約束とは何なのか説明してください。

Promise は、将来結果を生成する可能性のある値を生成するために使用される js 内のオブジェクトです。値は、解析された値、または値が解析されなかった理由の場合があります。

Promise には次の 3 つの状態があります。

保留中: 成功でも失敗でもない初期状態です。
満たされました: 操作が完全に成功したことを意味します。
拒否されました: 操作が失敗したことを意味します

待機状態の Promise オブジェクトは、成功後に値を返すか、失敗後にエラーを返すことができます。これら 2 つの状況が発生した場合、処理関数は実行のためにキューに入れられ、then メソッドが呼び出されます。

Resolve と拒否はそれぞれ 2 つの関数です。コールバックで呼び出されると、Promise インスタンスの状態が変更されます。解決は状態を成功に、拒否は失敗に変更します。

手書きの 約束

function Promise(exector) {
   
     let _this = this;  //status表示一种状态  let status = “pending“;  let value = undefined;  let reason = undefined;  //成功  function resolve(value) {
   
       if (status == “pending“) {
   
         _this.value = value;      _this.status = “resolve“;    }  }  //执行失败  function reject(value) {
   
       if (status == “pending“) {
   
         _this.value = value;      _this.status = “reject“    }  }  //异步操作  try {
   
       exector(resolve, reject)  } catch (e) {
   
       reject(e)  }  //测试then  Promise.prototype.then = function(reject, resolve) {
   
       let _this = this;    if (this.status == “resolve“) {
   
         reject(_this.value)    }    if (this.status == “reject“) {
   
         resolve(_this.reason)    }  }} //new Promise测试let promise = new Promise((reject,resolve)=>{
   
       resolve(“return resolve“);});promise.then(data => {
   
     console.log(`success${data}`);}, err => {
   
     console.log(`err${data}`);})

プロミスと非同期の違いは何ですか?

1. Async/Await とは
Async/await は新しい非同期コードの書き方です、使い方は同期の
async/await を Promise に基づいて実装したように見えますが、通常のコールバック関数には使用できません。
2. Promise とは何ですか?
これは、非同期の入れ子を解決し、コードを理解しやすくするために作成されました。
違い: async/await は、コードの同期性を高め、コードをさらに最適化します。

さまざまな非同期ソリューションの紹介

(1) コールバック関数(非同期コールバック)

コールバックは、別の関数にパラメータとして渡され、その関数の実行が終了した後に実行される関数です。

(2)約束 

Promise オブジェクトは、非同期プログラミング用の統一インターフェイスを提供するために commonJS ワーキング グループによって提案された仕様およびパターンです。

(3)非同期/待機

(4) イベント監視

イベント駆動型モデルを採用します。タスクの実行はコードの順序ではなく、イベントが発生するかどうかによって決まります。

(5) パブリッシュ/サブスクライブ

module.exportsとexportsの違いは何ですか?

モジュールとエクスポートは、Node.js によって各 js ファイルに組み込まれる 2 つのオブジェクトです。これは、console.log(module) および console.log(exports) を通じて出力できます。main.js に次の 2 行を記述して $node main.js を実行すると:

console.log(exports);//输出:{}console.log(module);//输出:Module {..., exports: {}, ...} (注:...代表省略了其他一些属性)

印刷すると、最初は module.exports と exports の両方が空のオブジェクト {} であることがわかります。実際、これら 2 つのオブジェクトは同じメモリを指しています。これは、module.exports と exports が同等であることを意味します (前提条件: それらが指すメモリ アドレスを変更しないでください)。

例:exports.age = 18 と module.export.age = 18、これら 2 つの記述方法は一貫しています (どちらも元の空のオブジェクト {} に属性を追加するのと同等であり、require によって取得される結果は {age: 18 です) }) 。

輸入と輸出とは何ですか?

インポートとエクスポートは、モジュール式の JS コードを作成するのに役立ちます。インポートとエクスポートを使用すると、コードを複数のファイルに分割できます。インポートでは、ファイルの特定の変数またはメソッドへのアクセスのみが許可されます。モジュールによってエクスポートされたメソッドまたは変数はインポートできます。​​​​​​​

 //index.js import name,age from './person';  console.log(name); console.log(age);
 //person.js let name ='Sharad', occupation='developer', age =26; export { name, age}; ​​​​​​​

元のリンク: JavaScript インタビューの質問からの基本的なインタビューの質問 (回答付き)

 

おすすめ

転載: blog.csdn.net/weixin_64948861/article/details/129271915
おすすめ