2023年フロントエンドインタビュー集
- jsの基本クラス
- Vue类
-
- 10. vue2 と vue3 の違い
- 11. ルートとルーターの違い
- 12. vue ルーティングの 2 つのモードの違い
- 13. キープアライブのライフサイクル
- 14. mvvm の利点:
- 15. 仮想DOMの役割
- 16. vue はどのようにしてパフォーマンスの最適化を実現しますか
- 17.ルートガード
- 18. Vue コンポーネント内のデータはなぜ関数でなければならないのですか?
- 19. ES6 の新機能は何ですか?
- 20. モジュール開発の利点:
- 21. JSON.stringify ディープコピーの欠点
- 22. 手ぶれ補正とスロットリングの違いは何ですか?
- 23. JS における Promise オブジェクトの役割と使用法
- 24. async-await 構文
- 25. マクロタスクとマイクロタスク
jsの基本クラス
1. プロトタイプチェーンとは何か、プロトタイプチェーンの存在意義
(1). プロトタイプチェーンとは
回答: プロトタイプ チェーンとは、各オブジェクトがプロトタイプ オブジェクトを持ち、オブジェクトがそのプロトタイプをテンプレートとして使用し、プロトタイプからメソッドとプロパティを継承することです。プロトタイプ オブジェクトにはプロトタイプがあり、そのプロトタイプからメソッドやプロパティをレイヤーごとに継承することもあります。この関係はプロトタイプチェーンと呼ばれます。
簡単に理解すると、プロトタイプ チェーンとは、現在のオブジェクトで定義が見つからない場合、定義が解除されるまで現在のオブジェクトのプロトタイプ オブジェクトを検索し続けるというものです。
(2). プロトタイプとプロトタイプチェーンの存在意義は何ですか?
回答: インスタンス オブジェクトは、コンストラクター プロトタイプのプロパティとメソッドを共有してメモリを節約できます。コンストラクター プロトタイプのプロパティとメソッドが多いほど、メモリの節約が大きくなります。
2. 範囲とは何ですか?
スコープは、1. グローバル スコープ、2. 関数スコープ、3. ブロック レベル スコープに分かれています。
回答: スコープとは、ランタイム コードの特定の部分にある変数、関数、オブジェクトへのアクセス可能性であり、コード ブロック内の変数やその他のリソースの可視性が決まります。
3. クロージャとは何ですか?
他の関数内の変数にアクセスできる関数はクロージャと呼ばれます。
この種のシーンでは、いくつかのイベント関数のカプセル化が使用され、
クロージャ自体が常駐メモリをもたらし、参照後に時間内に破棄されることはありません。
4. ブラウザのレンダリング処理
ブラウザに URL を入力すると、最終的には完全な Web ページが表示されます。次の手順を実行します。
1.HTMLの読み込み
ページに URL を入力すると、まず HTML ファイルが取得されます。HTML はページの基礎であるため、最初にダウンロードされ、ダウンロードが完了した後に解析されます。
2. 他の静的リソースのダウンロード
HTML 解析のプロセスで、CSS、JS、画像などの外部リソースのリンクが HTML テキスト内にある場合、他のスレッドがこれらの静的リソースをすぐにダウンロードできるようになります。ヘッド内で JS ファイルが検出されると、HTML 解析は停止します。JS ファイルがダウンロードされて実行された後も、HTML 解析作業は継続して、JS が完了した解析結果を変更するのを防ぎます。
上記のことから、ヘッドに配置された JS ファイルは同期読み込みに属し、DOM ツリーの構築をブロックし、ページの読み込みに影響を与えることがわかります。JSファイルが多いとページ白画面の時間も長くなります
5. データ型の概要:
js で一般的に使用される基本的なデータ型には、unknown - - (未定義)、null- - (空)、number - - (数値)、boolean- - (ブール値)、string- - (文字列)、Symbol - - ( シンボル) が含まれます。 );
js の参照データ型はオブジェクト型 Object- - (オブジェクト) です。たとえば、array - - (配列)、function - - (関数)、date - - (時刻) などです。
6.ディープコピー
浅いコピー: 浅いコピーとは、オブジェクトの各属性を順番にコピーすることですが、オブジェクトの属性値が参照型の場合、実際にコピーされるのはその参照であり、参照が指す値が変化するとコピーされます。も変わります
ディープ コピー: ディープ コピーとシャロー コピーは、複雑なデータ タイプ (オブジェクトと配列) 用です。シャロー コピーは 1 つのレイヤーのみをコピーしますが、ディープ コピーはレイヤーごとのコピーです。ディープ コピーでは変数の値がコピーされ、非基本型変数の場合は基本型変数まで再帰的にコピーされます。ディープ コピー後のオブジェクトは元のオブジェクトから完全に分離されており、相互に影響を与えません。一方のオブジェクトを変更しても、もう一方のオブジェクトには影響しません。
7. CSS の水平方向の中央揃えのいくつかの方法
- マージンと幅を実現し、コンテナ上で固定幅を定義し、マージンの左右の値を自動にします。
- コンテンツは inline-block と親要素 text-align:center を設定します。
- 絶対位置決めは水平方向のセンタリングを実現するもので、皆さんよくご存知だと思いますし、よく使うのではないでしょうか。
- css3 の flex 実装。
- css3のfit-content。
8. 配列に対してどのような実用的な高階関数が利用できるか知っていますか?
配列にはpushやpopなど簡単で便利なメソッドがたくさんありますが、実際に使われる高階関数もたくさんありますので、そのメソッドとシナリオをまとめてみましょう。 -order 関数: 高次関数。別の関数をパラメーターとして渡すことができる関数です。
クリックすると詳しい事例が表示されます
- それぞれに
- フィルター
- 地図
- 選別
- いくつかの
- 毎日
- 減らす
- 探す
9. 呼び出し、適用、バインドの違い
- call、apply、bind は同じです。これらはすべて this のポイントを変更し、渡された最初のパラメータが this をバインドするポイントです。非厳密モードでは、最初のパラメータが null または未定義の場合、グローバル オブジェクトはbe (ブラウザはウィンドウ) この値として、strict モードの場合、null は null、undefined は未定義であることに注意してください。
- call と apply の唯一の違いは、call はパラメーター リストでパスを渡し、apply は配列でパスを渡します。これはクラス配列にすることもできます。
- bind、call、apply の違い:bind は this のポイントを変更する関数を返します。これは、すぐに呼び出される call や apply とは異なり、後で呼び出すのに便利です。bind は call に似ており、パラメータ リストも同様です。渡されましたが、それ以上の可能性があります 一度渡すと、一度渡すだけで電話のような必要はありません
- 注目に値します。bind によって返された関数がコンストラクターとして new を使用する場合、バインドされた this 値は無効になり、this はインスタンス オブジェクトを指しますが、受信パラメータは依然として有効です (新しい呼び出しの優先順位 > バインド電話)
Vue类
10. vue2 と vue3 の違い
- 双方向データバインディングの原理が異なります
- 断片化をサポートするかどうか。
- API のタイプは異なります。
- データ変数の定義とメソッドは異なります。
- ライフサイクル フック関数は異なります。
- 父親と息子は異なる方法でパラメータを渡します。
- 命令はスロットとは異なります。
- main.js ファイルは異なります。
vue2: vue2 はフラグメントをサポートしていません。
vue3: vue3 はフラグメント (Fragments) をサポートします。つまり、複数のルート ノードを持つことができます。
vue2: vue2 の双方向データ バインディングは、ES5 の APIObject.definePropert() を使用してデータをハイジャックし、パブリッシュおよびサブスクライブ モードと組み合わせることで実現されます。
vue3: ES6 のプロキシ API は、vue3 でデータをプロキシするために使用されます。vue2.x と比較して、プロキシを使用する利点は次のとおりです:
(1).defineProperty は特定のプロパティのみを監視できますが、すべてのオブジェクトを監視
できるわけではありません (2).in では、クロージャなどのコンテンツを省略して効率を向上させることができます (ダイレクトバインディング (オブジェクト全体で十分)
(3). 配列を監視することができ、配列単体で特定の操作を行う必要がなく、Vue3.x では配列の内部データの変更を検出できます。
11. ルートとルーターの違い
router は VueRouter のインスタンスであり、グローバル ルーター オブジェクトと同等であり、多くの属性とサブオブジェクト (履歴オブジェクトなど) が含まれています。頻繁に使用されるジャンプ リンクには、ルーターリンク ジャンプと同じ this.$router.push を使用できます。
Route は現在のルーティング オブジェクトと同等です。いくつかのパラメータを取得でき、各ルートにはルーター オブジェクトがあり、そこから名前、パス、パラメータなどを取得できます。
12. vue ルーティングの 2 つのモードの違い
ハッシュ モードは、
URL の後の # 記号とそれに続く文字を指します。ページが更新されるたびに、# の後に直接変更されます。
ハッシュの原則: HTML の照準機能を柔軟に使用し、# の後のパスを変更すると、基本的に現在のページの照準ポイントが変更されるため、ページは更新されません。ブラウザの onhashchange() イベントの変更をリッスンして、対応するルーティング ルールを見つけます。
ハッシュ値の変更によってブラウザがサーバーにリクエストを送信することはなく、ハッシュ変更によって hashchange イベントがトリガーされるため (hashchange は # 以降の URL フラグメントのみを変更できます)、ハッシュ パスは URL に表示されますが、バックエンドにはまったく影響しないため、ハッシュ値を変更してもページはリロードされず、基本的にはハッシュを使用してフロントエンド ルーティングを実装します。
履歴モード
履歴の原理: H5 の履歴の 2 つの新しい API、pushState() と replaceState() およびイベント onpopstate を使用して、URL の変更を監視します。
back、forward、go メソッドが含まれます。履歴モード URL はバックエンドと一致している必要があるため、履歴に変更するにはバックエンドの協力も必要です。そうでない場合はエラーが報告されます。履歴を更新するたびに URL 全体が再リクエストされます。バックエンド、つまり再リクエストサーバーに送信します。バックエンドが時間内に応答しない場合、エラー 404 が報告されます。。
13. キープアライブのライフサイクル
コンポーネントの切り替えプロセス中、切り替えられたコンポーネントはメモリ内に保持されるため、DOM の繰り返しレンダリングが防止され、読み込み時間とパフォーマンスの消費が削減され、ユーザー エクスペリエンスが向上します。
キープアライブで作成されたコンポーネントには、さらに 2 つのライフサイクル フックがあります。アクティブ化 (コンポーネントがアクティブ化されるときに使用されます) と非アクティブ化 (コンポーネントが終了するときに呼び出されます) です。
フックのトリガー シーケンスは、作成 -> マウント -> アクティブ化され、終了時に非アクティブ化がトリガーされます。再度入力した場合(前方または後方)、アクティブ化のみがトリガーされます
キープアライブの使用法:
- プロジェクト全体をキャッシュする必要がある場合は、app.vue で router-view を keep-alive でラップするだけです。
- 一部のページをキャッシュするには、ルーティング アドレス設定のメタ属性に状態を追加し、app.vue でパッケージのルーター ビューを判断する必要があります。
- exclude と include を使用して、どのコンポーネントをキャッシュするか、どのコンポーネントをキャッシュしないかを指定することもできます。
14. mvvm の利点:
- mvc と mvvm は両方とも一種の設計思想であり、主に mvc のコントローラーが mvvm の viewModel に進化するという点です。Mvvm は主に、mvc 内の多数の dom 操作によってページのレンダリングのパフォーマンスと読み込み速度が向上するという問題を解決します。
- mvvm と mvc の最大の違いは、ビューとモデルの自動同期を実現していることです。モデルのプロパティが変更された場合、ビューの表示を変更するために dom 要素を手動で操作する必要はなく、自動的に変更されます。ドーム
- 全体として、mvvm は mvc よりもはるかに単純で、dom を頻繁に操作するためにセレクターを使用する必要はありません。
15. 仮想DOMの役割
- ビューと状態の関係を維持する
- 複雑なビュー状況でのレンダリング パフォーマンスの向上
- 実際の DOM を更新する前に、仮想 DOM は Diff アルゴリズムを使用して 2 つの新旧の仮想 DOM ツリー間の差異を比較し、部分的な更新を実現し、最終的に差異を実際の DOM に更新します。
16. vue はどのようにしてパフォーマンスの最適化を実現しますか
1. コードのモジュール化、一般的に使用される場所は個別のコンポーネントにカプセル化され、必要に応じて参照されます。繰り返しコードを書きすぎるのではなく、各コンポーネントは明確な意味を持たなければなりません。再利用性が高くなるほど、より良く、構成可能になります。型が強いほど、さらに、CSS を含めると、less と sass のカスタム CSS 変数を使用して、繰り返しコードを減らすこともできます。
2. Vue ルートは遅延読み込みに設定されており、最初の画面がレンダリングされるときにレンダリングを高速化できます。
3. パッケージ化の最適化、vue.config.js の構成項目を変更し、productionSourceMap を false に設定します。そうしないと、パッケージ化後に一部のマップ ファイルが生成されます。閉じていない場合、生成環境はマップを通じてソース コードを表示でき、有効にすることができます。 gzip 圧縮してパッケージを小さくします。
4. 画像の使用を減らすには、画像効果の代わりに CSS3 効果を使用するか、スプライト画像を使用して画像のサイズを小さくします。
5. オンデマンドでインポート。当社が使用する一部のサードパーティ ライブラリは、オンデマンドでインポートして読み込むことができます。不要な部分の導入や理由もなくプロジェクトのボリュームを増やすことは避けてください。
6. CDN を使用して、 vue-router、axios、その他の Vue 周辺プラグインなどの一部のリソースを外部からロードし、webpack.config.js および外部で不要なパッケージを設定します。参照されるモジュール
17.ルートガード
ルーティングガードの理解
ルーティング ガードには、グローバル ナビゲーション ガード、ルーティング ガード、コンポーネント ナビゲーション ガードの3 種類があります。ルーティングジャンプ自体は比較的複雑な処理ですが、この処理はナビゲーションガードによって洗練され、洗練されたそれぞれの処理(フック機能)内で対応する操作を実行できます。
ルートナビゲーションガード: ナビゲーションガードは、ルートジャンプの前後に何らかのフック機能です
ルートインターセプト: ルートが指定されたパスにジャンプする前に、手動で他のルーティングインターフェイスにジャンプさせることができ、ジャンプを停止することもできます。
ルーティング ガードの分類
1 グローバル ガード:
- グローバル フロント ガード: beforeEach は複数回トリガーされます。
- グローバル解像度ガード: beforeResolve 解像度ガード
- グローバル ポスト ガード: afterEach はコンポーネント インスタンス オブジェクトをコンポーネントの次のコールバックに渡します beforeRouteEnter ガード
2. ルーティングガード:
- beforeEnter ルートの専用ガード
3. コンポーネント内のガード:
- beforeRouteEnter はコンポーネントに入る前にトリガーし、コンポーネントに入るときに 1 回だけトリガーします
- beforeRouterUpdate コンポーネントが更新される前にトリガーされます (動的パラメーター変更クエリ文字列変更) コンポーネントに入った後、パラメーター変更を複数回トリガーできます
- beforeRouterLeave はルーティング コンポーネントを離れる前にトリガーし、コンポーネントを離れるときに 1 回だけトリガーします。
18. Vue コンポーネント内のデータはなぜ関数でなければならないのですか?
コンポーネントは共有できますが、そのデータはプライベートであるため、各コンポーネントは新しいデータ オブジェクト、一意のオブジェクトを返す必要があり、他のコンポーネントとオブジェクトを共有しないでください。
オブジェクト形式の場合、すべてのインスタンスが同じデータ オブジェクトを共有するため、コンポーネントがデータを変更すると、すべてのインスタンスが影響を受けるため、望ましくない結果になります。
このように、各インスタンスのデータ属性は独立しており、相互に影響を及ぼしません。これで、vue コンポーネントのデータが関数でなければならない理由がわかりました。これはすべて js 自体の特性によるもので、vue 自体の設計とは何の関係もありません。
19. ES6 の新機能は何ですか?
- 新增了块级作用域(let,const)
- 提供了定义类的语法糖(class)
- 新增了一种基本数据类型(Symbol)
- 新增了变量的解构赋值
- 函数参数允许设置默认值,引入了rest参数,新增了箭头函数。
- 数组新增了一些API,如isArray / from / of 方法;数组实例新增了 entries(),keys() 和 values() 等方法。
- 对象和数组新增了扩展运算符
- ES6新增了模块化(import / export)
- ES6新增了Set和Map数据结构。
- ES6原生提供Proxy构造函数,用来生成Proxy实例
- ES6新增了生成器(Generator)和遍历器(Iterator)
代入の構造化について話す
- 解构:分解数据结构。
- 赋值:为变量赋值。
- 解构赋值:从数组或者对象中提取值,按照对应的位置,对变量赋值(在数组解构中,只 要解构的目标可以遍历,就可以实现解构赋值)。
20. モジュール開発の利点:
- さまざまな汚染や名前の競合を避ける
- コードの再利用を改善する
- メンテナンス性の向上
- 簡単な依存関係管理
21. JSON.stringify ディープコピーの欠点
1. obj に時刻オブジェクトがある場合、JSON.stringify 後の JSON.parse の結果、時刻はオブジェクトの形式ではなく文字列の形式のみになります
。 3.オブジェクト
内に関数や未定義がある場合は、直接破棄されます
4. コンストラクターによって生成された json 内にオブジェクトがある場合、オブジェクトのコンストラクターは破棄されます
。 5. オブジェクト内に循環参照がある場合、ディープコピーは正しく実装できません
。 6. オブジェクト内に NAN がある場合、シリアル化後に null になります。
22. 手ぶれ補正とスロットリングの違いは何ですか?
開発中、次のようなシナリオが頻繁に発生します:mousemove でのマウスの動きの監視、scroll でのページスクロールの監視、resize でのサイズ変更の監視、入力の監視、ボタン検索、送信機能など。これらのシナリオでは、イベントは頻繁にトリガーされますが、イベントが頻繁にトリガーされることは望ましくありません。この場合、手ぶれ補正とスロットリングを使用して、頻繁な操作を制限する必要があります。
アンチシェイクとスロットリングは両方とも、イベントの頻繁なトリガーの問題を解決するためのものですが、実装原則にいくつかの違いがあります。具体的な実装原則については、以下を参照してください。
1.手ぶれ補正(デバウンス):
手ぶれ補正が高周波イベントをトリガーした場合、n 秒後に 1 回のみ実行され、n 秒以内に再度トリガーされた場合は再計算されます。
簡単な概要: 以前の遅延呼び出しは、トリガーされるたびにキャンセルされます。
アプリケーション シナリオ:
1. スクロール イベント スクロール
2. ブラウザ ウィンドウのズーム サイズ変更イベント
3. 検索ボックスにクエリが入力されたとき
4. フォーム検証
5. ボタン送信イベント
コード:
function debounce (fn, delay = 1000) {
let time = null
return function () {
// 获取当前this
let that = this
// 判断是否已经存在,如果存在直接清除
if (time) {
clearTimeout(time)
}
time = setTimeout(() => {
// 使fn 中this,执行当前调用者,并传入参数
fn.apply(that, arguments)
}, delay)
}
}
// 测试demo
function logger(e){
console.log('log -----')
}
btn.addEventListener('click',debounce(logger, 1000))
2. スロットル:
高頻度イベントトリガー。イベントがトリガーされるたびに遅延呼び出しメソッドを設定し、以前に遅延した呼び出しメソッドをキャンセルします。
簡単な概要: イベントがトリガーされるたびに、遅延関数の実行を待つかどうかが判断されます。
コード:
function throttle (fn, delay = 1000) {
let time = null;
return function () {
let that = this;
// 如果已经存在定时器了,则 不做处理
if (!time) {
time = setTimeout(() => {
fn.apply(that, arguments);
// 完结时,将time改为null
time = null;
}, delay);
}
};
}
違い:コールバックの実行頻度を減らし、コンピューティング リソースを節約します。
- 手ぶれ補正と絞りは本質が違います。アンチシェイクは複数の実行を最後の実行に変えること、スロットリングは
複数の実行を他のすべてのイベント実行に変えることです - 機能アンチシェイクによって継続的にトリガーする必要があるイベントは最後に 1 回だけ実行されますが、機能スロットリングは一定
期間内に 1 回だけ実行されます。
23. JS における Promise オブジェクトの役割と使用法
Promise は、非同期コードの記述を最適化するために ES6 によって提案された新しい構文です。
Promise の役割: ajax は非同期リクエストであり、多層の入れ子はコールバック地獄を引き起こします。Promise は同期をシミュレートします。また、非同期コールバックはビジネス ロジックを処理するための同期に似ています。
Promise の then メソッドは非同期メソッドですが、タイマーの前に実行されます。
1. Promise パラメータは関数であり、このコールバック関数には 2 つの仮パラメータ (カスタム、通常はsolve、reject として記述されます) があります。 2. Promise には 3 つの状態があります: 保留中
(待機中)、保留中 (成功)、拒否 (失敗)、渡されたパラメータ 解決、制御の拒否
3. 状態が送信されて変更されると、再度変更されることはありません。
4. .then のコールバック関数の実行に成功しますが、.catch のコールバック関数の実行に失敗します。
特徴:
非同期操作は同期操作のプロセスで表現され、ネストされたコールバック関数の層を回避します。
プロセスがより明確になり、コードがよりエレガントになりました。
Promise オブジェクトは、非同期操作の制御を容易にする統一インターフェイスを提供します。
欠点:
Promise はキャンセルできず、作成するとすぐに実行され、途中でキャンセルすることはできません。
コールバック関数が設定されていない場合、Promise 内でスローされたエラーは外部には反映されません。
保留状態の場合、現在どの段階まで進んでいるのか(開始したばかりか、完了間近か)を知ることはできません。
24. async-await 構文
async,await は es7 の新しい構文で、非同期コードの記述をさらに改善するために使用され、promise のアップグレード バージョンです。
非同期
- async 関数は Promise オブジェクトを返します。
- async 関数内の return ステートメントによって返される値は、Promise オブジェクトの値です。
function f1 () {
return 1
}
async function f2 () {
return 1
}
async function f3 () {
}
const r1 = f1()
const r2 = f2()
const r3 = f3()
console.log(r1) // 1
console.log(r2) // Promise, resolved(1)
console.log(r3) // Promise, resolved(undefined)
r2.then(res => {
console.log(res) })
r3.then(res => {
console.log(res) })
コマンドを待つ
- await の外部関数には async が必要です。
- 通常の状況では、await コマンドの後に Promise オブジェクトが続き、Promise の値が返されます。Promise オブジェクトではない場合は、対応する値を直接返します。
async関数内の実行フロー
- 非同期関数 (asyncF という名前) を実行する場合は、次の関数を入力します。
- 同期コードを順番に実行する
- awaitに遭遇し、asyncF関数から飛び出し、
- 後続のコードの実行を続けます。
- await後の非同期コードの実行が完了すると、asyncF内の後続のコードが実行されます。
25. マクロタスクとマイクロタスク
タスクが同期タスクと非同期タスクに分けられる理由
想像してみてください。js のタスクがすべて同期している場合、タイマーやネットワーク リクエストなど、遅延後に実行する必要があるタスクが発生した場合はどうなるでしょうか?
ページが麻痺している可能性があるため、実行に時間がかかるコードを待つために一時停止する必要があります
したがって、非同期タスクが導入されました。
● 同期タスク: 同期タスクは、コンソールなど、実行結果をすぐに確認するために待機する必要はありません。
● 非同期タスク: 非同期タスクは、setTimeout、ネットワーク リクエストなど、結果を確認するために一定時間待機する必要があります。
非同期タスクは、マクロ タスクとマイクロ タスクに細分化できます。以下は、これまでに学習したマクロタスクとミクロタスクのリストです。
● 最初に同期コードを実行します
。 ● マクロタスクに遭遇し、キューに入れます。
● マイクロタスクに遭遇し、マイクロタスク キューに入れます。
● 実行スタックは空です
。 ○ 実行のためにマイクロタスクをスタックにプッシュします
。 ● すべてのマイクロタスクが完了したら、マクロタスクキューの実装を実行する
マクロ タスクとマイクロ タスクを最初に実行するのは誰ですか? 回答: マクロ タスク