欧美一区二区三区老妇人-欧美做爰猛烈大尺度电-99久久夜色精品国产亚洲a-亚洲福利视频一区二区

golang中的不可變類型有哪些-創(chuàng)新互聯(lián)

golang中的不可變類型有哪些?可能很多人都不太了解,為了讓大家更加了解,小編給大家總結(jié)了以下內(nèi)容,希望大家根據(jù)這篇文章可以有所收獲。

創(chuàng)新互聯(lián)-專業(yè)網(wǎng)站定制、快速模板網(wǎng)站建設(shè)、高性價比平遙網(wǎng)站開發(fā)、企業(yè)建站全套包干低至880元,成熟完善的模板庫,直接使用。一站式平遙網(wǎng)站制作公司更省心,省錢,快速模板網(wǎng)站建設(shè)找我們,業(yè)務(wù)覆蓋平遙地區(qū)。費用合理售后完善,10余年實體公司更值得信賴。

Golang 中的不變性

如何利用不變性來增強你的 Golang 應(yīng)用程序的可讀性和穩(wěn)定性

不變性的概念非常簡單. 創(chuàng)建對象 (或結(jié)構(gòu)體) 后, 將永遠無法更改它. 這是一成不變的. 盡管這個概念看起來很簡單, 但使用它或從中受益并不那么容易.

正如計算機科學(xué) (和生活) 中的大多數(shù)事物一樣, 有許多種方法可以達到相同的結(jié)果, 就不變性而言, 兩者沒有什么不同. 您應(yīng)該把它看做是工具包中的一個工具, 并使用在適用的問題場景上. 關(guān)于不變性的一個非常好的用例是在您進行并發(fā)編程時. Golang 在設(shè)計時就考慮了并發(fā)性, 因此在 go 中使用并發(fā)非常普遍.

無論您使用哪種范例都可以通過以下方法在 Golang 中使用一些不變性概念來使代碼更具可讀性和穩(wěn)定性.

僅導(dǎo)出結(jié)構(gòu)體的功能, 而不導(dǎo)出其字段

這與封裝類似. 使用非導(dǎo)出字段創(chuàng)建結(jié)構(gòu), 僅導(dǎo)出作用的函數(shù). 由于您只對那些結(jié)構(gòu)的行為感興趣, 因此該技術(shù)對接口非常有用. 這項技術(shù)的另一個很好的補充是將創(chuàng)建函數(shù) (或構(gòu)造函數(shù)) 添加并導(dǎo)出到您的結(jié)構(gòu)中. 這樣您可以確保該結(jié)構(gòu)的狀態(tài)始終有效. 始終保持有效狀態(tài)可以使代碼更加可靠, 因為您不必繼續(xù)處理要對該結(jié)構(gòu)進行的每個操作的無效狀態(tài). 下面是一個非?;镜氖纠?

package amounts

import "errors"

type Amount struct {
    value int
}

func NewAmount(value int) (Amount, error) {
    if value < 0 {
        return Amount{}, errors.New("Invalid amount")
    }

    return Amount{value: value}, nil
}

func (a Amount) GetValue() int {
    return a.value
}

在此程序包中, 我們定義了 Amount 類型, 具有未導(dǎo)出的字段 value, 構(gòu)造函數(shù) NewAmount以及 GetValue 方法用于 Amount類型. 一旦 NewAmount 函數(shù)創(chuàng)建了 Amount 結(jié)構(gòu), 就無法更改它. 因此它從包的外部來說是不可變的 (盡管在 go 2 中有 更改此內(nèi)容的建議, 但 go 1 中沒有創(chuàng)建不變結(jié)構(gòu)的方法). 此外沒有處于無效狀態(tài) (在這種情況下為負數(shù)) 的 Amount 類型的變量, 因為創(chuàng)建它們的唯一方法已經(jīng)對此進行了驗證. 我們可以從另一個包中調(diào)用它:

a, err := amounts.NewAmount(10)
*// 處理錯誤
*log.Println(a.GetValue())

在函數(shù)中使用值拷貝替代指針

最基本的概念是在創(chuàng)建一個對象(或者結(jié)構(gòu)體)后,再也不去改變它。但是我們經(jīng)常在實體狀態(tài)很重要的應(yīng)用上工作。不過,程序中實體狀態(tài)和實體內(nèi)部表示是不同的。在使用不變性時,我們?nèi)匀豢梢越o實體賦予多個狀態(tài)。這意味著已創(chuàng)建的結(jié)構(gòu)體不會改變,但是它的副本會改變。這并不意味著我們需要手動實現(xiàn)復(fù)制結(jié)構(gòu)體中每個字段的功能。

相反地,當(dāng)調(diào)用函數(shù)時我們可以依賴 Go 語言復(fù)制值的本機行為。對于任意一個會改變實體狀態(tài)的操作,我們可以創(chuàng)建一個用來接收結(jié)構(gòu)體作為參數(shù)(或者作為函數(shù)接收器)的函數(shù),在執(zhí)行完畢之后返回改變后的版本。這是一項非常強大的技術(shù),因為你能夠改變副本上的任何內(nèi)容,而無需更改函數(shù)調(diào)用者作為參數(shù)傳遞的變量。這意味著沒有副作用和可預(yù)測的行為。如果相同的結(jié)構(gòu)體被傳遞給并發(fā)函數(shù),每個結(jié)構(gòu)體都會接收到它的副本,而不是指向它的指針。

當(dāng)你在使用切片功能時,你會看到此行為應(yīng)用于 [append](https://golang.org/pkg/builtin/#append) 函數(shù)

回到我們的例子中,讓我們實現(xiàn) Account 類型,它包含了
Amount 類型的 balance 字段。同時,我們添加 DepositWithdraw 方法來改變 Account 實體的狀態(tài)。

package accounts

import (
    "errors"
    "my-package/amounts"
)

type Account struct {
    balance amounts.Amount
}

func NewEmptyAccount() Account {
    amount, _ := amounts.NewAmount(0)
    return NewAccount(amount)
}

func NewAccount(amount amounts.Amount) Account {
    return Account{balance: amount}
}

func (acc Account) Deposit(amount amounts.Amount) Account {
    newAmount, _ := amounts.NewAmount(acc.balance.GetValue() + amount.GetValue())
    acc.balance = newAmount
    return acc
}

func (acc Account) Withdraw(amount amounts.Amount) (Account, error) {
    newAmount, err := amounts.NewAmount(acc.balance.GetValue() - amount.GetValue())
    if err != nil {
        return acc, errors.New("Insuficient funds")
    }
    acc.balance = newAmount
    return acc, nil
}

如果你檢查我們創(chuàng)建的方法,他們會覺得我們事實上改變了作為函數(shù)接收器的 Account 結(jié)構(gòu)的狀態(tài)。由于我們沒有使用指針,情況并非如此,由于結(jié)構(gòu)體的副本作為這些函數(shù)的接收器來傳遞,我們將更改只在函數(shù)作用域內(nèi)有效的副本,然后返回它。這是在另一個包中調(diào)用它的示例:

a, err := amounts.NewAmount(10)
acc := accounts.NewEmptyAccount()
acc2 := acc.Deposit(a)
log.Println(acc.GetBalance())
log.Println(acc2.GetBalance())

命令行上的結(jié)果會是這樣的:

2020/06/03 22:22:40 {0}
2020/06/03 22:22:40 {10}

如你所見,盡管通過變量 acc 調(diào)用了 Deposit 方法,但實際上變量并沒有改變,它返回了新的  Account 副本(分配給 acc2),其包含了改變后的字段。

使用指針具有優(yōu)于復(fù)制值的優(yōu)點,特別是如果您的結(jié)構(gòu)很大時,在復(fù)制時可能會導(dǎo)致性能問題,但是您應(yīng)始終問自己是否值得,不要嘗試過早地優(yōu)化代碼。尤其是在使用并發(fā)時。您可能會在一些糟糕的情況下結(jié)束。

減少全局或外部狀態(tài)中的依賴性

不變性不僅可以應(yīng)用于結(jié)構(gòu),還可以應(yīng)用于函數(shù)。如果我們用相同的參數(shù)兩次執(zhí)行相同的函數(shù),我們應(yīng)該收到相同的結(jié)果,對嗎?好吧,如果我們依賴于外部狀態(tài)或全局變量,則可能并非總是如此。最好避免這種情況。有幾種方法可以實現(xiàn)這一目標(biāo)。

如果您在函數(shù)內(nèi)部使用共享的全局變量,請考慮將該值作為參數(shù)傳遞,而不是直接在函數(shù)內(nèi)部使用。 那會使您的函數(shù)更可預(yù)測,也更易于測試。整個代碼的可讀性也會更容易,其他人也將會了解到值可能會影響函數(shù)行為,因為它是一個參數(shù),而這就是參數(shù)的用途。 這里有一個例子:

package main

import (
    "fmt"
    "time"
)

var rand int = 0

func main() {
    rand = time.Now().Second() + 1
    fmt.Println(sum(1, 2))
}

func sum(a, b int) int {
    return a + b + rand
}

這個函數(shù) sum 使用全局變量作為自己計算的一部分。 從函數(shù)簽名來看這不是很清楚。 更好的方法是將rand變量作為參數(shù)傳遞。 因此該函數(shù)看起來應(yīng)該像這樣:

func sum(a, b, rand **int**) **int** {
   return a + b + rand
}

看完上述內(nèi)容,你們對golang中的不可變類型有進一步的了解嗎?如果還想了解更多相關(guān)內(nèi)容,歡迎關(guān)注創(chuàng)新互聯(lián)成都網(wǎng)站設(shè)計公司行業(yè)資訊頻道,感謝各位的閱讀。

另外有需要云服務(wù)器可以了解下創(chuàng)新互聯(lián)scvps.cn,海內(nèi)外云服務(wù)器15元起步,三天無理由+7*72小時售后在線,公司持有idc許可證,提供“云服務(wù)器、裸金屬服務(wù)器、高防服務(wù)器、香港服務(wù)器、美國服務(wù)器、虛擬主機、免備案服務(wù)器”等云主機租用服務(wù)以及企業(yè)上云的綜合解決方案,具有“安全穩(wěn)定、簡單易用、服務(wù)可用性高、性價比高”等特點與優(yōu)勢,專為企業(yè)上云打造定制,能夠滿足用戶豐富、多元化的應(yīng)用場景需求。

當(dāng)前題目:golang中的不可變類型有哪些-創(chuàng)新互聯(lián)
分享地址:http://chinadenli.net/article34/pejse.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供網(wǎng)站建設(shè)用戶體驗、服務(wù)器托管電子商務(wù)、全網(wǎng)營銷推廣、品牌網(wǎng)站設(shè)計

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)

成都定制網(wǎng)站建設(shè)
欧美自拍系列精品在线| 国产激情国产精品久久源| 超薄丝袜足一区二区三区| 99久久精品视频一区二区| 日本国产欧美精品视频| 国产肥女老熟女激情视频一区| 成年人免费看国产视频| 欧美一级日韩中文字幕| 国产成人精品国产成人亚洲 | 日韩成人高清免费在线| 国产免费一区二区不卡| 男人把女人操得嗷嗷叫| 国产又色又爽又黄的精品视频| 欧美性猛交内射老熟妇| 日韩欧美一区二区黄色| 日本免费熟女一区二区三区| 欧美多人疯狂性战派对| 视频一区日韩经典中文字幕| 久一视频这里只有精品| 欧美精品专区一区二区| 毛片在线观看免费日韩| 国产午夜福利在线观看精品| 日本午夜福利视频免费观看| 日韩欧美黄色一级视频| 国产欧美高清精品一区| 欧美日韩最近中国黄片| 亚洲一区二区三区国产| 亚洲精品蜜桃在线观看| 国产亚洲视频香蕉一区| 国产精品二区三区免费播放心| 欧美人禽色视频免费看| 久久国产精品熟女一区二区三区| 中文字幕乱码免费人妻av| 丝袜视频日本成人午夜视频| 日本一级特黄大片国产| 亚洲成人黄色一级大片| 国产日韩综合一区在线观看| 成人精品亚洲欧美日韩| 国产精品一区二区视频| 国产欧美日韩一级小黄片| 国产精品一区二区视频成人|