試してみてください。新しい提案は信頼できますか?エラー処理を簡素化したい
プロポーザル: Go 2: エラー処理: ハンドラーを使用した try ステートメント[1]#」 ##》はコミュニティ内で白熱した議論を巻き起こしました。もう一度コミュニティと戦いましょう! ! ! 今日、Jianyu はこれを全員と一緒に公開し、これによって Go エラー処理メカニズムが開かれ、再編成できるかどうかを確認します。
背景提案作成者である PingCAP の @Greg Weber は 2 つの要素に基づいてこれを行います。1 つは「
Go 開発者アンケート 2022 年第 2 四半期の結果#」にあります。##[2]」と明記されています。

_, err := f() if err != nil { ... } _, err = r() if err != nil { ... } _, err = w() if err != nil { ... }
次のコード:
try err, handler
if err != nil { return handler(err) }
func(args...) (rtype1, rtypes..., rtypeN, error) { try err, handler ... }
func(args...) (rtype1, rtypes..., rtypeN, error) { if err != nil { return Zero(rtype1), Zeros(rtypes...)..., Zero(rtypeN), handler(err) } ... }
try err
if err != nil { return err }
x, err := f() try err, fmt.Errorf("f fail: %w", err)
func CopyFile(src, dst string) error { defer try func(err error) error { return fmt.Errorf("copy %s %s: %w", src, dst, err) } ... }
示例和实践
针对本提案,原作者给出了各类使用场景的示例。如下代码:
import ( "fmt" ) // This helper should be defined in the fmt package func Handlew(format string, args ...any) func(error) error { return func(err error) error { args = append(args, err) return fmt.Errorf(format+": %w", args...) } } // This helper should be defined in the fmt package func Handlef(format string, args ...any) func(error) error { return func(err error) error { args = append(args, err) return fmt.Errorf(format+": %v", args...) } } func valAndError() (int, error) { return 1, fmt.Errorf("make error") } func newGo() (int, error) { x, err := valAndError() try err // Common formatting functions will already be provided i := 2 x, err = valAndError() try err, Handlew("custom Error %d", i) // Using a custom error type // For convenience the error type can expose a method to set the error x, err = valAndError() try err, TheErrorAsHandler(i) } type TheError struct{ num int err error } func (t TheError) Error() String { return fmt.Sprintf("theError %d %v", t.num, t.err) } func TheErrorAsHandler(num int) func(err) TheError { return func(err error) TheError { return theError{ num: i, err: err } } }
另外在日常的 Go 工程中,提案作者认为 CopyFile 函数是新提案语句的一种很好的实践。为此基于 try-handler 进行了一版改造和说明。
如下代码:
// This helper can be used with defer func handle(err *error, handler func(err error) error) { if err == nil { return nil } *err = handler(err) } func CopyFile(src, dst string) (err error) { defer handle(&err, func(err error) error { return fmt.Errorf("copy %s %s: %w", src, dst, err) }) r, err := os.Open(src) try err defer r.Close() w, err := os.Create(dst) try err, func(err error) error { os.Remove(dst) // only if Create fails return fmt.Errorf("dir %s: %w", dst, err) } defer w.Close() err = io.Copy(w, r) try err err = w.Close() try err return nil }
引入 try-hanlder 后,能够做到:
插入错误的返回语句,进行机制预设。 在返回错误之前将错误处理函数组合在一起,便于后续的处理。
总结
在这个新提案中,一旦实施,就可以减少如下代码的编写:
if err != nil { return ... }
在代码编写上会节省一些行数,且可以为错误处理机制引入一些新的 ”操作“,这是该提案的优势。
但是从 Go 开发者的角度而言,会引入一些新的副作用,例如:初学者的学习成本、Go 工具链的改造、程序理解的复杂度增加。
另外新的语句,似乎比较难与 Go1.13 引入的 error.Is 和 As 有较好的相关联性。如果是做一个第三方用户库引入倒可以,但若是作为标准进入 Go 源代码中,似乎又有些格格不入(提案作者希望进入)。
看了那么多提案,Go 错误处理机制的 ”升级“,似乎陷入了手心手背都是肉的阶段...
以上が試してみてください。新しい提案は信頼できますか?エラー処理を簡素化したいの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ホットAIツール

Undresser.AI Undress
リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover
写真から衣服を削除するオンライン AI ツール。

Undress AI Tool
脱衣画像を無料で

Clothoff.io
AI衣類リムーバー

AI Hentai Generator
AIヘンタイを無料で生成します。

人気の記事

ホットツール

メモ帳++7.3.1
使いやすく無料のコードエディター

SublimeText3 中国語版
中国語版、とても使いやすい

ゼンドスタジオ 13.0.1
強力な PHP 統合開発環境

ドリームウィーバー CS6
ビジュアル Web 開発ツール

SublimeText3 Mac版
神レベルのコード編集ソフト(SublimeText3)

ホットトピック









Go では、関数のライフ サイクルには定義、ロード、リンク、初期化、呼び出し、戻り値が含まれます。変数のスコープは関数レベルとブロック レベルに分割されますが、ブロック内の変数はブロック内でのみ表示されます。 。

Go では、gorilla/websocket パッケージを使用して WebSocket メッセージを送信できます。具体的な手順: WebSocket 接続を確立します。テキスト メッセージを送信します。 WriteMessage(websocket.TextMessage,[]byte("message")) を呼び出します。バイナリ メッセージを送信します。WriteMessage(websocket.BinaryMessage,[]byte{1,2,3}) を呼び出します。

Go では、正規表現を使用してタイムスタンプを照合できます。ISO8601 タイムスタンプの照合に使用されるような正規表現文字列をコンパイルします。 ^\d{4}-\d{2}-\d{2}T \d{ 2}:\d{2}:\d{2}(\.\d+)?(Z|[+-][0-9]{2}:[0-9]{2})$ 。 regexp.MatchString 関数を使用して、文字列が正規表現と一致するかどうかを確認します。

Go と Go 言語は、異なる特性を持つ別個の存在です。 Go (Golang とも呼ばれます) は、同時実行性、高速なコンパイル速度、メモリ管理、およびクロスプラットフォームの利点で知られています。 Go 言語の欠点としては、他の言語に比べてエコシステムが充実していないこと、構文が厳格であること、動的型付けが欠如していることが挙げられます。

メモリ リークは、ファイル、ネットワーク接続、データベース接続などの使用されなくなったリソースを閉じることによって、Go プログラムのメモリを継続的に増加させる可能性があります。弱参照を使用してメモリ リークを防ぎ、強参照されなくなったオブジェクトをガベージ コレクションの対象にします。 go coroutine を使用すると、メモリ リークを避けるために、終了時にコルーチンのスタック メモリが自動的に解放されます。

IDE を使用して Go 関数のドキュメントを表示する: 関数名の上にカーソルを置きます。ホットキーを押します (GoLand: Ctrl+Q; VSCode: GoExtensionPack をインストールした後、F1 キーを押して「Go:ShowDocumentation」を選択します)。

並行関数の単体テストは、同時環境での正しい動作を確認するのに役立つため、非常に重要です。同時実行機能をテストするときは、相互排他、同期、分離などの基本原則を考慮する必要があります。並行機能は、シミュレーション、競合状態のテスト、および結果の検証によって単体テストできます。

Golang では、エラー ラッパーを使用して、元のエラーにコンテキスト情報を追加することで新しいエラーを作成できます。これを使用すると、さまざまなライブラリまたはコンポーネントによってスローされるエラーの種類を統一し、デバッグとエラー処理を簡素化できます。手順は次のとおりです。errors.Wrap 関数を使用して、元のエラーを新しいエラーにラップします。新しいエラーには、元のエラーのコンテキスト情報が含まれています。 fmt.Printf を使用してラップされたエラーを出力し、より多くのコンテキストとアクション性を提供します。異なる種類のエラーを処理する場合は、errors.Wrap 関数を使用してエラーの種類を統一します。
