目錄
提案" >提案
總結" >總結
首頁 後端開發 Golang Go大佬良心發現,願意給 map 加清除了?

Go大佬良心發現,願意給 map 加清除了?

Aug 04, 2023 pm 05:20 PM
go


一個東西來來回回的討論,關了又開,關了後建新的,新的被ban 了,又發現新的論據,再打開新的。這在職場工作中很常見,在 Go 的提案討論中,也出現了...

今天要分享的是 Go map 在 NaN 上的一個爭議和可能即將出現的 API 增加。

背景與考題

NaN 是什麼

在電腦科學中,有一個神奇的值,叫做:NaN(Not a Number,非數)。它是數值資料類型的一類值,表示未定義或不可表示的值。常在浮點數運算中使用。首次引進 NaN 的是 1985 年的 IEEE 754 浮點數標準。

在 NaN 值的儲存和比較時,會有問題。因為判斷一個值是否為 NaN 時,不能以判斷 x=NaN 或 x≠NaN 來比較。但因為 NaN 永遠不等於其自身,因此可判斷 x=x 或 x≠x 來判斷 x 是否為 NaN 值,將會分別回傳 False 和 True。

當 NaN 與另一個浮點數 x(其中 x 可為正常值、正負無窮大或 NaN)進行比較時,比較結果如下:

##比較結果#NaN ≥ xFalse NaN ≤ xFalse#NaN > xFalse#NaN FalseNaN = xFalseNaN ≠ x# ## ###真的###########

這裡的理解對於下面的考題很重要。

Go IEEE-754 考題

在Go101 上看到一道關於IEEE-754 浮點數的題,我在這裡引用題目,以下程式碼輸出什麼?

如下程式碼:

package main

import "math"

func main() {
 a, b, c := 2.0, 1.0, 0.0
 x, y := a/c, b/c     // infinity
 n := math.NaN()      // not a number
 m := math.Sqrt(-1.0) // not a number
 println(x == y, m == n)
}
登入後複製
  • A:true true。
  • B:true false。
  • C:false false。
  • D:false true。

答案是啥?是 A 嗎,還是 D?

對上述程式進行解析,變數 x,y 是 Inf 正無窮。 m,n 是 NaN 無窮值。

正確的答案是:B。

你答對了嗎?

提案

在對 NaN 有了基本的了解後,我們可以正式進入主題了。在Go map 關聯提案中,常提到新增API,用於滿足清空map 的訴求:

Go大佬良心發現,願意給 map 加清除了?

但在多次討論中,Go 官方團隊給出的解決方案是:

for k := range m {
    delete(m, k)
}
登入後複製

並關閉了相關的提案,結束了這個議題。留下滿臉 」好吧,這都行「 的疑惑打工人的我們,這是這類提案的背景。

但這塊有一個坑,在包含任何 NaN 鍵值時,將無法透過循環 delete 的方式清空 map。一旦你 map 有 NaN,但你又 for delete,以為刪掉了,其實並沒有,就會產生類似洩漏的效果。

因此 Go 團隊的靈魂人物 Russ Cox,重新發起了新提案《proposal: spec: add delete(m) to clear map[1]》。如下圖:

Go大佬良心發現,願意給 map 加清除了?

希望藉此來解決 NaN 的 map 問題,並同時完成一直以來討論的 map 清空/重置/清理等社區訴求。

也就是新增,如下特性:

delete(m)
登入後複製

支援清除 map 的功能(即使包含 NaN)。

總結

針對這個提案也有幾種聲音,分別是萬惡的命名,對叫 delete,還是叫 clear 都有不同的見解。

// Clear removes all entries from m, leaving it empty.
func Clear[M ~map[K]V, K comparable, V any](m M "M ~map[K]V, K comparable, V any")

delete(m)
登入後複製

也有声音提到不允许引入 NaN 值,但显然。在 Go1 已经很难了,因为 NaN 已经被允许引入,球已经在锅里了。

Go大佬良心發現,願意給 map 加清除了?

对于 map 新增 API 用于清空/重置/清除的作用,你怎么看呢?还是说你也更喜欢对 NaN 单独的处理?例如 panic?

以上是Go大佬良心發現,願意給 map 加清除了?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn

熱AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Clothoff.io

Clothoff.io

AI脫衣器

Video Face Swap

Video Face Swap

使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的程式碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

強大的PHP整合開發環境

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發工具

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

Go WebSocket 訊息如何發送? Go WebSocket 訊息如何發送? Jun 03, 2024 pm 04:53 PM

在Go中,可以使用gorilla/websocket包發送WebSocket訊息。具體步驟:建立WebSocket連線。傳送文字訊息:呼叫WriteMessage(websocket.TextMessage,[]byte("訊息"))。發送二進位訊息:呼叫WriteMessage(websocket.BinaryMessage,[]byte{1,2,3})。

深入理解 Golang 函數生命週期與變數作用域 深入理解 Golang 函數生命週期與變數作用域 Apr 19, 2024 am 11:42 AM

在Go中,函數生命週期包括定義、載入、連結、初始化、呼叫和返回;變數作用域分為函數級和區塊級,函數內的變數在內部可見,而區塊內的變數僅在區塊內可見。

如何在 Go 中使用正規表示式匹配時間戳記? 如何在 Go 中使用正規表示式匹配時間戳記? Jun 02, 2024 am 09:00 AM

在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函數檢查字串是否與正規表示式相符。

Golang 與 Go 語言的區別 Golang 與 Go 語言的區別 May 31, 2024 pm 08:10 PM

Go和Go語言是不同的實體,具有不同的特性。 Go(又稱Golang)以其並發性、編譯速度快、記憶體管理和跨平台優點而聞名。 Go語言的缺點包括生態系統不如其他語言豐富、文法更嚴格、缺乏動態類型。

Golang 技術效能優化中如何避免記憶體洩漏? Golang 技術效能優化中如何避免記憶體洩漏? Jun 04, 2024 pm 12:27 PM

記憶體洩漏會導致Go程式記憶體不斷增加,可通過:關閉不再使用的資源,如檔案、網路連線和資料庫連線。使用弱引用防止記憶體洩漏,當物件不再被強引用時將其作為垃圾回收目標。利用go協程,協程棧記憶體會在退出時自動釋放,避免記憶體洩漏。

如何在 IDE 中查看 Golang 函數文件? 如何在 IDE 中查看 Golang 函數文件? Apr 18, 2024 pm 03:06 PM

使用IDE檢視Go函數文件:將遊標停留在函數名稱上。按下熱鍵(GoLand:Ctrl+Q;VSCode:安裝GoExtensionPack後,F1並選擇"Go:ShowDocumentation")。

Golang 函數接收 map 參數時的注意事項 Golang 函數接收 map 參數時的注意事項 Jun 04, 2024 am 10:31 AM

在Go中傳遞map給函數時,預設會建立副本,對副本的修改不影響原map。如果需要修改原始map,可透過指標傳遞。空map需小心處理,因為技術上是nil指針,傳遞空map給期望非空map的函數會發生錯誤。

如何使用 Golang 的錯誤包裝器? 如何使用 Golang 的錯誤包裝器? Jun 03, 2024 pm 04:08 PM

在Golang中,錯誤包裝器允許你在原始錯誤上追加上下文訊息,從而創建新錯誤。這可用於統一不同程式庫或元件拋出的錯誤類型,簡化偵錯和錯誤處理。步驟如下:使用errors.Wrap函數將原有錯誤包裝成新錯誤。新錯誤包含原始錯誤的上下文資訊。使用fmt.Printf輸出包裝後的錯誤,提供更多上下文和可操作性。在處理不同類型的錯誤時,使用errors.Wrap函數統一錯誤類型。

See all articles