首頁 > 軟體

Golang易錯知識點彙總

2022-09-06 18:06:01

型別轉換和型別斷言

型別轉換語法:Type(expression)

型別斷言語法為:expression.(Type)

1.型別轉換範例程式碼

package main

import "fmt"

//典型的型別轉換範例
func main() {
   // 型別轉換範例
   var a int = 5
   var b int = 2
   var c float32
   c = float32(a) / float32(b) //這裡就是典型的型別轉換
   fmt.Printf("a的型別:%Tn", a)
   fmt.Printf("b的型別:%Tn", b)
   fmt.Printf("c的型別:%Tn", c)
   fmt.Printf("c的值:%vn", c)
   //如果我們不進行型別轉換,看下輸出結果
   fmt.Printf("不進行型別轉換的輸出結果:%vn", a/b) //從結果可以看出值為2,丟失了精度
}

列印結果

2.型別斷言程式碼範例

注意:對於型別斷言,expression 必須是介面型別

package main

import "fmt"

//經典的型別斷言範例 搭配switch使用
func main() {
   var x interface{}
   x = 1
   switch x.(type) { //這就是上面說的expression.(Type)
   case float32:
      fmt.Println("型別是:float32")
   case string:
      fmt.Println("型別是:string")
   case int:
      fmt.Println("型別是:int")
   default:
      fmt.Println("未知型別")
   }
}

執行結果

全域性變數

定義全域性變數必須用var,全域性變數要定義在函數之外,而在函數之外定義的變數只能用var定義。

全域性變數使用var,編譯通過

全域性變數不使用var,編譯不通過

init函數

這是官方對於init()函數的介紹:

變數除了可以在全域性宣告中初始化,也可以在 init ()函數中初始化。這是一類非常特殊的函數,它不能夠被人為呼叫,而是在每個包完成初始化後自動執行,並且執行優先順序比 main 函數高。 初始化總是以單執行緒執行,並且按照包的依賴關係順序執行。 一個可能的用途是在開始執行程式之前對資料進行檢驗或修復,以保證程式狀態的正確性。

如何覺得上面這一大段話不好理解的話,可以看我的總結:

  • init函數可以在任何包中有0個、1個或多個;
  • main函數只能在main包中有且只有一個,但是main包中也可以有0個、1個或多個init函數;
  • init函數和main函數都不能被顯式呼叫;

Go語言中變數、init函數、main函數的執行順序

  • 首先初始化匯入包的變數和常數
  • 然後執行匯入包的init函數
  • 然後初始化本包的變數和常數
  • 然後執行本包的init函數
  • 最後執行本包的main函數

Go介面總結

這是我在刷題的時候碰到的,總結出來給大家:

  • 如果兩個介面擁有相同方法列表(順序可以不一致),那麼這兩個介面實質上同一個介面
  • 介面A是介面B的子集,意味著A的方法B中都有,那麼A是B的基礎類別,所以A=B是可行的
  • 介面是否能夠呼叫成功,需要執行的時候才能知道
  • 介面賦值是否可行,在編譯階段就可以知道

Go字串

Go語言中的字串不支援下標操作

在go語言中,字串是一種基本型別,和其它開發語言不同,Go的字串是由單個位元組連線起來的。

Go語言統一使用utf-8編碼標識Unicode文字。當字元為ASCII編碼時,佔用1個位元組,其它字元佔用2到4個位元組,中文佔用3個位元組

如何修改字串的內容

有三種方法:

  • 將字串轉成byte切片,再根據下標替換內容
  • 將字串轉為rune切片,再根據下標替換內容
  • 使用原生包 strings 中的 Replace() 方法

範例程式碼

package main

import (
   "fmt"
   "strings"
)

func main() {
   //第一種方法 將字串轉成byte切片
   s := "hello"
   s2 := []byte(s)
   s2[0] = 'x'
   fmt.Printf("轉成byte切片:%vn", string(s2)) //列印結果:轉成byte切片:xello

   // 第二種方法 將字串轉為rune切片
   s3 := "王中陽"
   s4 := []rune(s3) //注意:中文字串要進行修改,只能轉成rune切片,不能轉成byte切片
   s4[0] = '楊'
   fmt.Printf("轉成rune切片:%vn", string(s4)) //列印結果:轉成rune切片:楊中陽

   // 第三種方法,使用原生包strings 中的 Replace() 方法
   s5 := "abcdef"
   old := "abc"
   newString := "ABC"
   s6 := strings.Replace(s5, old, newString, -1) //最後一個引數n的作用是:返回將s5中前n個不重疊old子串都替換為new的新字串,如果n<0會替換所有old子串。
   fmt.Printf("strings替換之後的:%vn", s6)           //列印結果:strings替換之後的:ABCdef
}

執行結果

slice

slice可以通過append方式實現元素的刪除。

**切片使用冒號分隔時遵循"前閉後開"原則,即包括前面的值,不包括後面的值。 **

1.刪除單個元素

package main

import "fmt"

//使用append 刪除單個元素
func main() {
   var data = []int{0, 1, 2, 3, 4, 5}
   //刪除元素2
   index := 2
   //切片使用冒號分隔時遵循"前閉後開"原則,即包括前面的值,不包括後面的值。
   data1 := append(data[:index], data[index+1:]...)
   fmt.Println(data1)
}

執行結果

2.刪除多個元素

package main

import "fmt"

//使用append 刪除多個元素
func main() {
   var data = []int{0, 1, 2, 3, 4, 5}
   //刪除元素0,1,2
   index := 2
   //切片使用冒號分隔時遵循"前閉後開"原則,即包括前面的值,不包括後面的值。
   data1 := append(data[:0], data[index+1:]...)
   fmt.Println(data1)
}

執行結果

總結

這篇文章彙總了我再開發和刷面試題過程中遇到的容易搞錯的知識點,包括:

  • 型別轉換和型別斷言的對比
  • 定義全域性變數只能用var,定義全域性變數也可以定義在init()函數中
  • init()函數的知識點,以及init函數和main函數的執行順序:先執行參照包的常數和變數、在執行參照包的init函數、再執行本包的常數和變數、再執行本包的init函數、最後才會執行本包的main函數。
  • Go介面的概念總結,刷面試題的時候可能碰到咬文嚼字的問題,注意避坑。
  • Go字串不能通過下標直接修改內容,但是可以通過轉成byte[]/rune[]/以及使用原生包strings中的Replace()方法修改內容
  • Go中的slice不能像map一樣直接使用delete()方法刪除元素,可以使用append()方法+冒號分隔切片的方式,間接實現切片元素的刪除。

到此這篇關於Golang易錯知識點彙總的文章就介紹到這了,更多相關Golang知識點內容請搜尋it145.com以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援it145.com!


IT145.com E-mail:sddin#qq.com