zoukankan      html  css  js  c++  java
  • 13-接口

    什么是接口

    接口就是一系列方法的集合

    当一个结构体定义了接口中的所有方法,我们称它实现了该接口。这与面向对象编程(OOP)的说法很类似。接口指定了一个类型应该具有的方法,并由该类型决定如何实现这些方法

    语法

    type 接口名 interface{
        方法一
        方法二
    }

    接口的声明与实现

    package main
    import "fmt"
    
    //定义一个鸭子接口(一系列方法的集合)
    type Duck interface {
        run()
        speak()
    }
    //定义普通鸭子结构体(一系列属性的集合)
    type PDuck struct {
        name string
        age int
    }
    //定义唐老鸭的结构体
    type TDuck struct {
        name string
        age int
        wife bool
    }
    
    //实现run方法
    func (p PDuck)run()  {
        fmt.Println(p.name,"我在走路")
    }
    //实现speak方法
    func (p PDuck)speak()  {
        fmt.Println(p.name,"我在讲话")
    }
    
    //唐老鸭实现接口(实现两个方法)
    func (T TDuck)run()  {
        fmt.Println(T.name,"我在走路")
    }
    func (T TDuck)speak()  {
        fmt.Println(T.name,"我在说话")
    }
    func main() { pD:
    =PDuck{name:"水鸭子"} //结构体赋值 tD:=TDuck{name:"唐老鸭"} pD.speak() //实现接口方法 tD.speak() var p Duck //通过接口直接访问方法 p=pD p.speak() } #结果 水鸭子 我在讲话 唐老鸭 我在说话 水鸭子 我在讲话

    类型断言

    func speak(p Duck)  {
        switch a:=p.(type) {
        case PDuck:
            //判断好了,你是普通鸭子,把鸭子名字拿出来
            fmt.Println("你是普通鸭子")
            fmt.Println(a.name)
        case TDuck:
            //判断好了,你是唐老鸭,把唐老鸭的wife拿出来
            fmt.Println("你是唐老鸭")
    
            fmt.Println(a.wife)
        }
    }

    空接口

    没有包含方法的接口称为空接口。空接口表示为 interface{}。由于空接口没有方法,因此所有类型都实现了空接口

    package main
    import "fmt"
    
    type Empty interface {    //空接口
    
    }
    type TDuck2 struct {
        name string
        age string
        wife bool
    }
    func main() {
        test(1)
        test("ssss")
        test(TDuck2{})
        test(10.45)
    }
    
    func test(a interface{})  {  //因为test函数接收空接口作为参数,因此可以给这个函数传递任何类型。用interface{}接收空接口
        switch a.(type) {    //做断言判断
        case int:
            fmt.Println("你是int类型")
        case string:
            fmt.Println("你是string ")
        case TDuck2:
            fmt.Println("你是唐老鸭")
        default:
            fmt.Println("我不知道你是什么类型")
    
        }
    }

    实现多个接口

    就是一个结构体实现多个接口的方法

    package main
    import (
        "fmt"
    )
    
    type SalaryCalculator interface {
        DisplaySalary()
    }
    
    type LeaveCalculator interface {
        CalculateLeavesLeft() int
    }
    
    type Employee struct {
        firstName string
        lastName string
        basicPay int
        pf int
        totalLeaves int
        leavesTaken int
    }
    
    func (e Employee) DisplaySalary() {
        fmt.Printf("%s %s has salary $%d", e.firstName, e.lastName, (e.basicPay + e.pf))
    }
    
    func (e Employee) CalculateLeavesLeft() int {
        return e.totalLeaves - e.leavesTaken
    }
    
    func main() {
        e := Employee {
            firstName: "Naveen",
            lastName: "Ramanathan",
            basicPay: 5000,
            pf: 200,
            totalLeaves: 30,
            leavesTaken: 5,
        }
        e.DisplaySalary()
        e.CalculateLeavesLeft()
        fmt.Println("
    Leaves left =", e.CalculateLeavesLeft())
        //除了上面可以直接用e.方法名获得,还可以按照下面这种写法
        //var s SalaryCalculator = e     //把e赋值给了SalaryCalculator类型的接口变量
        //s.DisplaySalary()           //然后调用DisplaySalary方法
        //var l LeaveCalculator = e      //把e赋值给了LeaveCalculator类型的接口变量
    }
    #结果
    Naveen Ramanathan has salary $5200
    Leaves left = 25

    接口的嵌套

    尽管 Go 语言没有提供继承机制,但可以通过嵌套其他的接口,创建一个新接口。

    package main
    
    import (  
        "fmt"
    )
    
    type SalaryCalculator interface {  
        DisplaySalary()
    }
    
    type LeaveCalculator interface {  
        CalculateLeavesLeft() int
    }
    
    type EmployeeOperations interface {   //嵌套了接口,就可以使用接口的方法
        SalaryCalculator
        LeaveCalculator
    }
    
    type Employee struct {  
        firstName string
        lastName string
        basicPay int
        pf int
        totalLeaves int
        leavesTaken int
    }
    
    func (e Employee) DisplaySalary() {  
        fmt.Printf("%s %s has salary $%d", e.firstName, e.lastName, (e.basicPay + e.pf))
    }
    
    func (e Employee) CalculateLeavesLeft() int {  
        return e.totalLeaves - e.leavesTaken
    }
    
    func main() {  
        e := Employee {
            firstName: "Naveen",
            lastName: "Ramanathan",
            basicPay: 5000,
            pf: 200,
            totalLeaves: 30,
            leavesTaken: 5,
        }
        var empOp EmployeeOperations = e
        empOp.DisplaySalary()
        fmt.Println("
    Leaves left =", empOp.CalculateLeavesLeft())
    }
    #结果
    Naveen Ramanathan has salary $5200
    Leaves left = 25

    接口的零值

    接口的零值nil,所以接口是引用类型

    package main
    
    import "fmt"
    
    type Describer interface {  
        Describe()
    }
    
    func main() {  
        var d1 Describer
        if d1 == nil {
            fmt.Printf("d1 is nil and has type %T value %v
    ", d1, d1)
        }
    }
  • 相关阅读:
    【HTTP】长连接和短连接
    HTTP/1.1 持久连接 persistent connection
    浅谈Websocket、Ajax轮询和长轮询(long polling)
    web通信之跨文档通信 postMessage
    HTML5 postMessage 和 localStorage 实现窗口间通信
    CORS 和 JSONP
    【转】js中几种实用的跨域方法原理详解
    [跨域]前端解决跨域问题
    RFC1867 HTTP file upload
    Multipart/form-data POST文件上传
  • 原文地址:https://www.cnblogs.com/wangcuican/p/12035423.html
Copyright © 2011-2022 走看看