JSON データを処理するときは、通常、 json.Unmarshal 関数を使用して、JSON 文字列を Go 言語の構造に解析します。ただし、UnmarshalJSON 関数内で json.Unmarshal 関数を呼び出すと、スタック オーバーフロー エラーが発生する可能性があります。これは、UnmarshalJSON 関数が JSON データの解析時に自分自身を再度呼び出し、無限ループを引き起こすためです。これを回避するには、json.Unmarshal 関数を直接呼び出す代わりに、json.Decoder の Decode メソッドを使用して JSON データを解析します。これにより、スタック オーバーフローの問題が発生せず、コードの堅牢性とパフォーマンスが保証されます。
UnmarshalJSON
の実装でデータ構造を初期化するためにいくつかの追加手順を実行したいと考えています。この実装で json.Unmarshal(b, type)
を呼び出すと、当然スタック オーバーフローが発生します。
JSON デコーダは、json.Unmarshal
を再度呼び出す前に、カスタム UnmarshalJSON
実装があるかどうかの検索を続けます。
これを行う他の方法はありますか?基礎となるデフォルト実装を呼び出すだけではこの問題が発生しないでしょうか?
この状況を回避/防止する簡単で一般的な方法は、type
キーワードを使用し、typeconversion を使用することです。 その型の値を渡します (新しい型は元の型を基礎となる型として持つため、元の値である場合は型変換できます)。
これが機能するのは、type
キーワードが新しい型を作成し、その新しい型にはメソッドがまったく含まれない (基本型のメソッドを「継承」しない) ためです。
これにより実行時のオーバーヘッドが発生しますか?いいえ。 仕様から引用: 変換:
例を見てみましょう。 Age
という数値を持つ person
タイプがあり、Age
が負の値 (0
未満) にならないようにしたいと考えています。 。
出力 (
Go Playgroundで試してください): リーリー もちろん、同じ手法がカスタム マーシャリングにも適用されます (
MarshalJSON()):
リーリー
### 試して: ###
リーリー
出力 (同じ
の例):
リーリー パッケージのカスタム テキスト表現に対してString() string メソッドを定義し、次のことを行う場合です。変更したデフォルトの文字列表現を使用するには。詳細については、こちらをご覧ください: t と *t
的自定义文本表示定义 の違い
以上がUnmarshalJSON 関数内で json.Unmarshal を呼び出してもスタック オーバーフローが発生しないの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。