Menulis kod selamat memori dalam Go adalah penting untuk mengelakkan ranap program, kerosakan data dan kelemahan keselamatan. Amalan termasuk: menghantar penunjuk, menggunakan kapasiti kepingan, mengelakkan limpahan penimbal, menggunakan kepingan dengan berhati-hati, menggunakan make() untuk membuat kepingan dan peta, menggunakan tangguh untuk melepaskan sumber dan menggunakan penyegerakan.Mutex untuk menyegerakkan akses serentak. Mengikuti amalan ini boleh meningkatkan keteguhan dan kebolehpercayaan kod anda dan dapat dilihat dalam kes praktikal.
Menulis kod selamat memori dalam Go adalah penting untuk mengelakkan ranap program, kerosakan data dan kelemahan keselamatan. Mengikuti amalan berikut boleh membantu meningkatkan keteguhan dan kebolehpercayaan kod anda.
Petunjuk lulus (*T
)而不是值(T
)可以防止意外修改传入的值。例如:
func Swap(a, b *int) { *a, *b = *b, *a }
切片([]T
)基于底层数组,因此了解其容量至关重要。容量表示数组的最大长度。超过容量时,Go 会自动分配一个更大的底层数组,从而改变切片的地址。
以下代码演示了这一点:
s := []int{1, 2, 3} println(len(s), cap(s)) // 3 3 s = append(s, 4) println(len(s), cap(s)) // 4 6
缓冲区溢出会发生在存储的数据量超出分配给它的缓冲区时。在 Go 中,可以使用以下方法避免这种情况:
copy()
函数:copy()
确保复制的数据量不超过目标缓冲区的容量。切片不是内存安全类型,因为它们共享底层数组。对切片进行修改可能会意外影响其他使用同一数组的变量。
以下示例说明了这一点:
s1 := []int{1, 2, 3} s2 := s1[1:] s1[0] = 4 println(s1) // [4 2 3] println(s2) // [2 3]
make()
创建切片和映射使用 make()
显式创建切片和映射可以指定其初始容量,从而避免不必要的分配。
defer
来释放资源defer
语句可确保代码块在函数返回之前执行。这对于释放资源(例如打开的文件或网络连接)非常有用。
以下示例使用 defer
来关闭文件:
func main() { file, err := os.Open("file.txt") if err != nil { return } defer file.Close() // 执行其他操作 }
sync.Mutex
sync.Mutex
是用于同步并发访问共享资源的互斥锁。Mutex
可以通过 Lock()
和 Unlock()
方法来获取和释放锁。
以下示例使用 sync.Mutex
来保护对共享数据的并发访问:
var mu sync.Mutex var count int func main() { for i := 0; i < 10; i++ { go func() { mu.Lock() defer mu.Unlock() count++ }() } // 等待所有协程完成 }
考虑一个计算两个切片交集的函数:
func Intersection(s1, s2 []int) []int { var res []int for _, v1 := range s1 { for _, v2 := range s2 { if v1 == v2 { res = append(res, v1) } } } return res }
通过遵循以下原则,我们可以提高这个函数的内存安全性:
copy()
函数来安全地追加元素。make()
func Intersection(s1, s2 []int) []int { res := make([]int, 0, min(len(s1), len(s2))) for _, v1 := range s1 { for _, v2 := range s2 { if v1 == v2 { copy(res[len(res):], []int{v1}) } } } return res }
Kepingan (
Kod berikut menunjukkan perkara ini:
rrreee🎜Mengelakkan Limpahan Penampan🎜🎜Limpahan penimbal berlaku apabila jumlah data yang disimpan melebihi penimbal yang diperuntukkan kepadanya. Dalam Go, ini boleh dielakkan menggunakan kaedah berikut: 🎜copy()
: copy()
untuk memastikan jumlah data yang disalin tidak melebihi kapasiti penimbal sasaran. 🎜🎜🎜Gunakan kepingan dengan berhati-hati🎜🎜Kepingan bukan jenis yang selamat untuk ingatan kerana ia berkongsi tatasusunan asas. Pengubahsuaian pada kepingan mungkin secara tidak dijangka mempengaruhi pembolehubah lain yang menggunakan tatasusunan yang sama. 🎜🎜Contoh berikut menggambarkan perkara ini: 🎜rrreee🎜Gunakan make()
untuk membuat kepingan dan peta 🎜🎜Gunakan make()
untuk mencipta kepingan dan peta secara eksplisit untuk menentukan permulaannya keupayaan untuk mengelakkan peruntukan yang tidak perlu. 🎜🎜Gunakan tunda
untuk melepaskan sumber 🎜🎜Pernyataan tunda
memastikan bahawa blok kod dilaksanakan sebelum fungsi kembali. Ini berguna untuk membebaskan sumber seperti fail terbuka atau sambungan rangkaian. 🎜🎜Contoh berikut menggunakan tunda
untuk menutup fail: 🎜rrreee🎜Menggunakan sync.Mutex
🎜🎜sync.Mutex
digunakan untuk menyegerakkan serentak akses kepada kunci Mutex kongsi untuk sumber. Mutex
boleh memperoleh dan melepaskan kunci melalui kaedah Lock()
dan Unlock()
. 🎜🎜Contoh berikut menggunakan sync.Mutex
untuk melindungi akses serentak kepada data kongsi: 🎜rrreee🎜Contoh praktikal🎜🎜Pertimbangkan fungsi yang mengira persilangan dua keping: 🎜rrreee🎜Dengan mengikuti perkara berikut prinsip, kami Keselamatan memori fungsi ini boleh dipertingkatkan: 🎜copy()
untuk menambahkan elemen dengan selamat. 🎜make()
untuk membuat kepingan secara eksplisit. 🎜🎜🎜Kod penambahbaikan terakhir adalah seperti berikut: 🎜rrreee🎜Mengikuti amalan ini membantu menulis fungsi Go yang selamat memori dan meningkatkan keteguhan, kebolehpercayaan dan keselamatan kod. 🎜Atas ialah kandungan terperinci Amalan pengaturcaraan keselamatan memori fungsi Golang. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!