go階段性開發(fā)總結(jié)筆記精華

最近基于gin嘗試寫了一套內(nèi)部使用的框架(如下)驴一,過程中有一些總結(jié)筆記在此記錄。

1灶壶、打開連接如MySQL肝断,redis要記得close,否則容易內(nèi)存泄漏驰凛;

2胸懈、for循環(huán)的時(shí)候 要注意 最好顯式close。其實(shí)當(dāng)我們通過for循環(huán)迭代數(shù)據(jù)庫的時(shí)候恰响,當(dāng)?shù)阶詈笠粯訑?shù)據(jù)的時(shí)候趣钱,會(huì)出發(fā)一個(gè)io.EOF的信號(hào),引發(fā)一個(gè)錯(cuò)誤胚宦,同時(shí)go會(huì)自動(dòng)調(diào)用rows.Close方法釋放連接首有,然后返回false,此時(shí)循環(huán)將會(huì)結(jié)束退出枢劝。通常你會(huì)正常迭代完數(shù)據(jù)然后退出循環(huán)井联。可是如果并沒有正常的循環(huán)而因其他錯(cuò)誤導(dǎo)致退出了循環(huán)您旁。此時(shí)rows.Next處理結(jié)果集的過程并沒有完成低矮,歸屬于rows的連接不會(huì)被釋放回到連接池。因此十分有必要正確的處理rows.Close事件被冒。如果沒有關(guān)閉rows連接军掂,將導(dǎo)致大量的連接并且不會(huì)被其他函數(shù)重用,就像溢出了一樣昨悼。最終將導(dǎo)致數(shù)據(jù)庫無法使用蝗锥。所以為了避免這種情況的發(fā)生,最好的辦法就是顯示的調(diào)用rows.Close方法率触,確保連接釋放终议,又或者使用defer指令在函數(shù)退出的時(shí)候釋放連接,即使連接已經(jīng)釋放了,rows.Close仍然可以調(diào)用多次穴张,是無害的细燎。rows.Next循環(huán)迭代的時(shí)候,因?yàn)橛|發(fā)了io.EOF而退出循環(huán)皂甘。為了檢查是否是迭代正常退出還是異常退出玻驻,需要檢查rows.Err。

3偿枕、切片可以理解為不定長數(shù)組 璧瞬,map可以理解為 key:value 對(duì)格式;map聲明后不能直接進(jìn)行賦值渐夸,只有初始化后才能進(jìn)行賦值操作嗤锉。

4、gin中件間攔截請(qǐng)求墓塌,總在路由請(qǐng)求之前執(zhí)行,即 http攔截器瘟忱,再到路由邏輯。在注冊(cè)中間件代碼之后的路由才生效中間件規(guī)則苫幢;

5懈玻、全局變量或者 路由之外(main函數(shù))的東西批狱,都會(huì)一直保存值不消失(常駐內(nèi)存)输涕,要特別注意內(nèi)存泄露埂淮。啟動(dòng)后就不會(huì)重新賦值棒拂,而不是每次請(qǐng)求(生命周期) 會(huì)重新賦值伞梯,注意。實(shí)踐證明:不是每次請(qǐng)求都重新清空賦值的帚屉,特別是全局變量谜诫;比如DB全局句柄實(shí)例的close不同請(qǐng)求會(huì)互相影響。還有一個(gè)指針取地址要特別小心共享問題攻旦。

6喻旷、結(jié)構(gòu)體傳地址和傳值的區(qū)別,在于函數(shù)內(nèi)改變形參值牢屋,會(huì)不會(huì)影響外部的實(shí)參且预。定義指針和形參 用*,函數(shù)內(nèi)部則用&? 代表取地址烙无。指針賦值锋谐,這點(diǎn)原理和C指針相通。

7截酷、只有大結(jié)構(gòu)體涮拗,全局變量適合用指針傳值(指針變量其實(shí)就是個(gè)指向變量的地址)。普通對(duì)象指針用多了會(huì)發(fā)生內(nèi)存逃逸,導(dǎo)致gc壓力過大三热。 go官方一些規(guī)范里面鼓择,也是推薦一般情況下使用傳值。

8就漾、真實(shí)內(nèi)存占用量就是物理內(nèi)存占用量減去buffer和cache的占用量呐能。

9、MySQL庫自帶連接池从藤,使用方不需自行實(shí)現(xiàn)催跪。*sql.DB 線程安全,開箱即用夷野,屏弊了底層創(chuàng)建連接的實(shí)現(xiàn)

Open 只是創(chuàng)建類懊蒸,調(diào)用一次即可,使用前需要 Ping 確保連接正常悯搔。

一定要設(shè)置連接池的兩個(gè)參數(shù) MaxIdle, MaxOpen骑丸,否則在極端情況會(huì)把 DB 連接打滿(未加索引,大事務(wù)阻塞)妒貌⊥ㄎ#可選 MaxLifetime,需咨詢 DBA灌曙,一般 DB 默認(rèn)8小時(shí)菊碟,無需設(shè)置,如果很短要視情況而定

事務(wù)會(huì)占用一個(gè)連接在刺,盡可能減小事務(wù)耗時(shí)逆害,打散大事務(wù),否則會(huì)將 DB 連接數(shù)打滿

prepare 會(huì)占用一個(gè)連接蚣驼,每次使用完后魄幕,一定要 close ,否則同樣會(huì)將連接數(shù)打滿

DSN 需要指定時(shí)區(qū)和對(duì)時(shí)間字段的支持颖杏,否則會(huì)出現(xiàn)時(shí)間提前8小時(shí)的問題

Query, Prepare, Exec 無需業(yè)務(wù)層重試纯陨,底層已經(jīng)實(shí)現(xiàn)

使用var != nil判斷實(shí)現(xiàn)的懶漢式單例并不是線程安全的,注意GO的單例有多種實(shí)現(xiàn)方式留储。

10翼抠、init函數(shù)在加載包的時(shí)候也就是編譯服務(wù)啟動(dòng)的時(shí)候就已經(jīng)執(zhí)行了而不是等執(zhí)行HTTP請(qǐng)求的時(shí)候執(zhí)行到路由才執(zhí)行。所有init函數(shù)是接收不到query參數(shù)來初始化的获讳。

11机久、redigo? 連接池pool:TCP 連接保持, 客戶端和服務(wù)端各自都保持不斷開赔嚎,可以重用TCP膘盖。

12胧弛、關(guān)于接口:

接口可以等于任何一個(gè)實(shí)現(xiàn)它的 結(jié)構(gòu)體的實(shí)例,然后調(diào)用實(shí)例 中的 接口方法侠畔。比如定義cache接口结缚,用Redis和M實(shí)例來各自實(shí)現(xiàn)接口方法。比如 redigo包软棺『旖撸空接口= 沒有方法的接口,接口變量可以等于任何東西喘落,任何東西默認(rèn)都實(shí)現(xiàn)了空接口茵宪。已經(jīng)基礎(chǔ)入門

13瘦棋、閉包就是對(duì) 變量有個(gè)全局的 作用稀火。解決? 變量作用域問題。

14赌朋、go build? 打包命令

go build -o test example/example.go 命令啥意思

go build主要用于編譯代碼

打包命令凰狞,格式:go build [-o output] [-i] [build flags] [packages]

? ? 其中:-o 指定打包后輸出的文件名.exe,文件名后面跟的是需要打包的.go文件

打包方式1:

? ? 切換到項(xiàng)目目錄下沛慢,執(zhí)行打包命令:

? ? cd $GOPATH/src/myfirstgo

? ? go build

? ? 此時(shí)生成的打包文件名為項(xiàng)目目錄名,這里為myfirstgo

? ? 也可以指定輸出包名赡若,示例: go build -o abc

? ? ? ? 或者 go build -o abc main.go

打包方式2:

? ? 在其他目錄執(zhí)行以下命令:

? ? ? ? go build myfirstgo 此時(shí)在當(dāng)前執(zhí)行命令目錄生成myfirstgo可執(zhí)行文件

? ? 指定輸出包名,示例: go build -o xyz myfirstgo 此時(shí)在當(dāng)前執(zhí)行命令目錄生成xyz可執(zhí)行文件

? ? 在非go項(xiàng)目目錄下執(zhí)行”go build 路徑+項(xiàng)目名“命令查找的項(xiàng)目目錄從$GOPATH/src/開始

15团甲、注意if寫法或者遍歷時(shí)逾冬,變量的作用域。

比如如下寫法是編譯不通過的:

func JsonStr2Map(str string)(map[string]interface{},error){

var dat map[string]interface{}

? if err :=json.Unmarshal([]byte(str), &dat);err !=nil {

return nil,err

? }

return dat,err

}

正確寫法:

func JsonStr2Map(str string)(map[string]interface{},error){

var dat map[string]interface{}

? if err :=json.Unmarshal([]byte(str), &dat);err !=nil {

return nil,err

? }else {

return dat,err//注意err作用域

? }

}

16躺苦、json轉(zhuǎn)結(jié)構(gòu)體索引問題

type Email struct {

Email string `json:"email_address"`

}

type EmailsList struct {

IsSchemaConforming bool `json:"isSchemaConforming"`

? SchemaVersion? ? ? int? `json:"schemaVersion"`

? Emails []Email `json:"unknown.0"`

}

jsonStr := `{"isSchemaConforming":true,"schemaVersion":0,"unknown.0":[{"email_address":"test1@uber.com"},{"email_address":"test2@uber.com"}]}`

emails := EmailsList{}

json.Unmarshal([]byte(jsonStr), &emails)

email0? := emails.Emails[0].Email //注意這里emails.Emails["0"].Email?和emails.Emails['0'].Email 都不正確身腻,注意它們的區(qū)別

17、注意if語句代碼塊中變量的作用域?yàn)榫植康?/p>

以下兩種寫法的區(qū)別:

v,ok :=sActivityId.(string)

if !ok {

return nil,errors.New("type err")

}

return v

以下代碼編譯錯(cuò)誤:

if v,ok :=sActivityId.(string);!ok{

return nil,errors.New("type err")

}

return v

18圾另、斷言的語法是接口類型的霸株,其他類型無法使用斷言語法雕沉。數(shù)組值為接口類型的字符串集乔,strconv.ParseInt(v,10,64)? string轉(zhuǎn)int行傳參時(shí)必須先將接口類型斷言為string。

19坡椒、golang中new和make的區(qū)別

make 僅用來分配及初始化類型為 slice扰路、map、chan 的數(shù)據(jù)倔叼。new 可分配任意類型的數(shù)據(jù)(包括結(jié)構(gòu)體).

new 分配返回的是指針汗唱,即類型 *Type。make 返回引用丈攒,即 Type.

new 分配的空間被清零, make 分配空間后哩罪,會(huì)進(jìn)行初始化.

總結(jié)

new 的作用是初始化一個(gè)指向類型的指針(*T)授霸,make 的作用是為 slice,map 或 chan 初始化并返回引用(T)际插。

func new(Type) *Type? ? 自己實(shí)現(xiàn)一個(gè)類似 new 的功能:

func newInt() *int {?

var i int?

return &i?

}

someInt := newInt()

我們這個(gè)函數(shù)的功能跟 someInt := new(int) 一模一樣碘耳。所以在我們自己定義 new 開頭的函數(shù)時(shí),出于約定也應(yīng)該返回類型的指針框弛。


func make(Type, size... IntegerType) Type? ? ?內(nèi)建函數(shù) make 用來為 slice辛辨,map 或 chan 類型分配內(nèi)存和初始化一個(gè)對(duì)象(注意:只能用在這三種類型上),跟 new 類似瑟枫,第一個(gè)參數(shù)也是一個(gè)類型而不是一個(gè)值斗搞,跟 new 不同的是,make 返回類型的引用而不是指針慷妙,而返回值也依賴于具體傳入的類型僻焚,具體說明如下:

Slice: 第二個(gè)參數(shù) size 指定了它的長度,它的容量和長度相同景殷。?

你可以傳入第三個(gè)參數(shù)來指定不同的容量值溅呢,但必須不能比長度值小。?

比如 make([]int, 0, 10)

Map: 根據(jù) size 大小來初始化分配內(nèi)存猿挚,不過分配后的 map 長度為 0咐旧,如果 size 被忽略了,那么會(huì)在初始化分配內(nèi)存時(shí)分配一個(gè)小尺寸的內(nèi)存

Channel: 管道緩沖區(qū)依據(jù)緩沖區(qū)容量被初始化绩蜻。如果容量為 0 或者忽略容量铣墨,管道是沒有緩沖區(qū)的

20、初始化結(jié)構(gòu)體的三種方法

a:=new(user)

b:=&user{}

c:=user{}

type?user?struct?{

????id?int?`1123`

}

func?main()?{

????a?:=?&user{}

????a.id?=?111

????b?:=?user{}

????b.id?=?222

????c?:=?new(user)

????c.id?=?333

????fmt.Println(a,?b,?c)

}

?運(yùn)行后結(jié)果如下

&{111}?{222}?&{333}

a:=new(user) <== 創(chuàng)建user變量办绝,并且清零 b:=&user{} <== 返回的是user變量的指針 c:=user{} <== 創(chuàng)建user變量伊约,三種寫法的效果完全一樣,區(qū)別只是 語法糖 的差異而已孕蝉。

小馬不茍同上面這句話屡律,雖然從上面結(jié)果看三種寫法效果是一樣的,但是本質(zhì)有區(qū)別降淮。a?:=?&user{}是取地址超埋,c?:=?new(user)是取地址并清零,b?:=?user{}是拷貝佳鳖。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
禁止轉(zhuǎn)載霍殴,如需轉(zhuǎn)載請(qǐng)通過簡信或評(píng)論聯(lián)系作者。
  • 序言:七十年代末系吩,一起剝皮案震驚了整個(gè)濱河市来庭,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌穿挨,老刑警劉巖月弛,帶你破解...
    沈念sama閱讀 207,248評(píng)論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件肴盏,死亡現(xiàn)場離奇詭異,居然都是意外死亡帽衙,警方通過查閱死者的電腦和手機(jī)叁鉴,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,681評(píng)論 2 381
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來佛寿,“玉大人幌墓,你說我怎么就攤上這事〖叫海” “怎么了常侣?”我有些...
    開封第一講書人閱讀 153,443評(píng)論 0 344
  • 文/不壞的土叔 我叫張陵,是天一觀的道長弹渔。 經(jīng)常有香客問我胳施,道長,這世上最難降的妖魔是什么肢专? 我笑而不...
    開封第一講書人閱讀 55,475評(píng)論 1 279
  • 正文 為了忘掉前任舞肆,我火速辦了婚禮,結(jié)果婚禮上博杖,老公的妹妹穿的比我還像新娘椿胯。我一直安慰自己,他們只是感情好剃根,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,458評(píng)論 5 374
  • 文/花漫 我一把揭開白布哩盲。 她就那樣靜靜地躺著,像睡著了一般狈醉。 火紅的嫁衣襯著肌膚如雪廉油。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,185評(píng)論 1 284
  • 那天苗傅,我揣著相機(jī)與錄音抒线,去河邊找鬼。 笑死渣慕,一個(gè)胖子當(dāng)著我的面吹牛嘶炭,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播摇庙,決...
    沈念sama閱讀 38,451評(píng)論 3 401
  • 文/蒼蘭香墨 我猛地睜開眼旱物,長吁一口氣:“原來是場噩夢(mèng)啊……” “哼遥缕!你這毒婦竟也來了卫袒?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,112評(píng)論 0 261
  • 序言:老撾萬榮一對(duì)情侶失蹤单匣,失蹤者是張志新(化名)和其女友劉穎夕凝,沒想到半個(gè)月后宝穗,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,609評(píng)論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡码秉,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,083評(píng)論 2 325
  • 正文 我和宋清朗相戀三年逮矛,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片转砖。...
    茶點(diǎn)故事閱讀 38,163評(píng)論 1 334
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡须鼎,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出府蔗,到底是詐尸還是另有隱情晋控,我是刑警寧澤,帶...
    沈念sama閱讀 33,803評(píng)論 4 323
  • 正文 年R本政府宣布姓赤,位于F島的核電站赡译,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏不铆。R本人自食惡果不足惜蝌焚,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,357評(píng)論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望誓斥。 院中可真熱鬧只洒,春花似錦、人聲如沸劳坑。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,357評(píng)論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽泡垃。三九已至析珊,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間蔑穴,已是汗流浹背忠寻。 一陣腳步聲響...
    開封第一講書人閱讀 31,590評(píng)論 1 261
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留存和,地道東北人奕剃。 一個(gè)月前我還...
    沈念sama閱讀 45,636評(píng)論 2 355
  • 正文 我出身青樓,卻偏偏與公主長得像捐腿,于是被迫代替她去往敵國和親纵朋。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,925評(píng)論 2 344

推薦閱讀更多精彩內(nèi)容