GO语言使用之面向对象编程(5)面向对象三大特征之封装

一、封装介绍

封装(encapsulation)就是把抽象出的字段和对字段的操作封装在一起,数据被保护在内部,程序的其它包只有通过被授权的操作(方法),才能对字段进行操作。

二、对封装的理解和使用封装好处

1、 隐藏代码具体实现细节
2)、提可以对数据进行验证,保证安全合理(比如年龄(Age))

三、如何体现封装

1) 对结构体中的属性进行封装
2) 通过方法,包 实现封装

四、封装的实现步骤

1、将结构体、字段(属性)的首字母小写(不能导出了,其它包不能使用,类似private)
2、 给结构体所在包提供一个工厂模式的函数,首字母大写。类似一个构造函数
3、提供一个首字母大写的Set方法(类似其它语言的public),用于对属性判断并赋值

func (var 结构体类型) SetXxx(形参列表)  (返回值列表) {
    //对数据验证,进行处理 var.字段名
}

4、提供一个首字母大写的Get方法(类似其它语言的public),用于获取属性的值

func (var 结构体的类型) GetXxx() 返回值 {
    return  var.字段  
       }

特别说明:在Golang开发中并没有特别强调封装,这点并不像Java. 所以提醒学过java 的朋友,无需用java的语法特性来看待Golang, Golang本身对面向对象的特性做了简化的.

五、快速入门案例

银行账户案例:
1)创建程序,在model包中定义Account结构体:在main函数中体会Golang的封装性。
2) Account结构体要求具有字段:账号(长度在6-10之间)、余额(必须>20)、密码(必须是六位)
3) 通过SetXxx的方法给Account 的字段赋值 通过GetXxx方法获取字段的值。(同学们自己完
4) 将前面的Account单独的放在model包,并改进即可。
5) 在main函数中测试
代码如下:
model/account.go

package model
import (
    "fmt"
)

// 名字:Account
// 属性/字段
// 账号, 余额, 密码...

// 行为/方法
// 存钱
// 取钱
// 查询..

type account struct {
    accountNo string
    money float64
    pwd string
}
//工厂模式

func checkField(accountNo string, money float64, pwd string) bool {

    //先对值进行验证
    if len(accountNo) < 6 || len(accountNo) > 10 {
        fmt.Println("账号长度不对")
        return false
    } 

    if money <= 20 {
        fmt.Println("余额不对")
        return false
    }

    if len(pwd) != 6 {
        fmt.Println("密码需要为6位")
        return false
    }

    return true

}

func NewAccount(accountNo string, money float64, pwd string) *account {

    if !checkField(accountNo , money , pwd) {

        return nil
    }

    return &account{
        accountNo : accountNo,
        money : money,
        pwd : pwd,
    }
}
//克隆..
func CloneAccount(account *account) *account {

    return &account{
        accountNo : account.accountNo,
        money : account.money,
        pwd : account.pwd,
    }
}


//给accountNo 方法
func (a *account) GetAccountNo() string {
    return a.accountNo
}
//账号不能修改,因此不提供Set..

func (a *account) GetPwd() string {
    return a.pwd
}

func (a *account) SetPwd(pwd string) bool {
    if len(pwd) != 6 {
        fmt.Println("密码需要为6位")
        return false
    } else {
        a.pwd = pwd
        return true
    }
}

//对Money的封装

func (a *account) Deposite(money float64, pwd string) {

    if pwd != a.pwd {
        fmt.Println("密码不正确")
        return 
    }

    if money <= 0 {
        fmt.Println("存入的金额不对")
        return 
    }

    //存款
    a.money += money
    fmt.Println("恭喜,存款ok")
}


func (a *account) WithDraw(money float64, pwd string) {

    if pwd != a.pwd {
        fmt.Println("密码不正确")
        return 
    }

    if money <= 0 || money > a.money {
        fmt.Println("取款金额不对..")
        return 
    }

    //取款
    a.money -= money
    fmt.Println("恭喜,取款ok")
}

func (a *account) Query(pwd string) {

    if pwd != a.pwd {
        fmt.Println("密码不正确")
        return 
    }
    //你的余额
    fmt.Println("你的余额", a.money)
}

main/main.go

package main
import (
    "go_code/chapter11/encapsulation/model"
)


func main() {

    //使用一把
    account := model.NewAccount("gh000001", 99999.9, "000000")



    account.Deposite(10, "000000")
    account.Query("000000")

    account.WithDraw(8000, "000000")
    account.Query("000000")



}

猜你喜欢

转载自blog.csdn.net/TDCQZD/article/details/81712301