zoukankan      html  css  js  c++  java
  • go 语言 interface(接口 二)

    1.空接口,interface{}

    空接口类型interface{}一个方法签名也不包含,所以所有的数据类型都实现了该方法。

    空接口类型在描述一个对象实例的行为上力不从心,但是当我们需要存储任意数据类型的实例的时候,空接口类型的使用使得我们得心应手。

    如果一个函数的参数包括空接口类型interface{},实际上函数是在说“兄弟,我接受任何数据”。如果一个函数返回一个空接口类型,那么函数再说“我也不确定返回什么,你只要知道我一定返回一个值就好了”。

    package main
    
    
    import (
    	"fmt"
    )
    
    func main(){
    	var a interface{}
    	var b int = 1000
    
    	a = b
    	fmt.Println(a)         //1000
    
    	var c string = "hello"
    	a = c
    	fmt.Println(a)         //hello
    }
    

      2.接口嵌套

    package main
    
    import (
    	"fmt"
    )
    
    type Eater interface {
    	Eat()
    }
    
    type Talker interface {
    	Talk()
    }
    
    type Animal interface {   //接口嵌套  字段直接写上其它接口的名字,也可以定义其它的方法集合
    	Eater
    	Talker
    }
    
    type Dog struct {
    }
    
    func (d *Dog) Eat() {
    	fmt.Println("eating")
    }
    
    func (d *Dog) Talk() {
    	fmt.Println("eating")
    }
    
    type Cat struct {
    }
    
    func (c *Cat) Eat() {
    	fmt.Println("eating")
    }
    
    func (c *Cat) Talk() {
    	fmt.Println("eating")
    }
    func main() {
    	d := &Dog{}
    	var a Animal
    	a = d
    	a.Eat()               //eating
    }
    

    3.类型断言

    就是说如何知道接口里存储的对象的类型

    func testassertion() {
    	var a int
    	var i interface{}
    	a = 100
    	i = a
    	y := i.(int)           //类型转换
    	fmt.Println(y)    //100
    }
    func testassertion() {
    	var a int
    	var i interface{}
    	a = 100
    	i = a
    	// y := i.(int)
    	y := i.(string)             //类型转换,转换成  string
    	fmt.Println(y)              //panic: interface conversion: interface {} is int, not string
    }
    上面的例子没有判断,一旦类型转换失败程序运行会中断,下面会加上判断
    func testassertion() {
    	var a int
    	var i interface{}
    	a = 100
    	i = a
    	// y := i.(int)
    	y, ok := i.(string)    
    	if !ok {           //判断
    		fmt.Println("this is not string")
    		return
    	}
    	fmt.Println(y)
    }
    

     4.上面的判断局限性比较大,下面我们用swtich来判断,这样可以覆盖基本的数据类型

    package main
    
    
    
    import (
    	"fmt"
    )
    
    func justify(items ...interface{}) {
    	for index, v := range items {
    		switch v.(type) {     //判断传入参数的类型
    		case int:
    			fmt.Printf("第 %d 个参数 is int
    ", index)
    		case int32:
    			fmt.Printf("第 %d 个参数 is int32
    ", index)
    		case float32:
    			fmt.Printf("第 %d 个参数 is float32
    ", index)
    		
    		}
    	}
    }
    
    func main(){
    	var a int
    	var b float32
    	var c int32
    	justify(a, b, c)
    
    	
    }
    //运行结果
    第 0 个参数 is int
    第 1 个参数 is float32
    第 2 个参数 is int32
    

      5.判断变量是否实现了接口

    import (
    	"fmt"
    )
    
    type SSSS interface {   //定义接口
    	sing(s string)
    }
    type Man struct {
    	Name string
    }
    
    func (m *Man) sing(name string) {  //实现接口
    	fmt.Printf("%s is la la la la %s", m.Name, name)
    }
    func main() {
    	var s SSSS
    	m := &Man{
    		Name: "xiao ming",
    	}
    	s = m
    	fmt.Println(s)
    	fmt.Println(m.Name)
    	var n interface{}
    	n = m    //把m存入n这个空接口
    	if sv, ok := n.(SSSS); ok {  //判断n是否实现SSSS这个接口
    		sv.sing("爱在回首间")
    	}
        
    }
    //运行结果:
    &{xiao ming}
    xiao ming
    xiao ming is la la la la 爱在回首间
    

    6.以上的例子给我们展示了一个接口类型如何存储满足他的的数据类型实例,并且展示给我们如何创建存储不同数据类型实例的集合。

    利用此思想,我们还可以让函数来接受满足特定接口类型的数据类型实例。

    举例来说,我们已经知道fmt.Print 是一个可变参数的函数,他可以接受任意数量的参数。但是你有没有注意到,有时候我们使用的是strings、ints和floats?

    事实上,如果你深入去看fmt包,你就会看到如下的接口声明:

    //The Stringer interface found in fmt package
    type Stringer interface {
         String() string
    }

    任何数据类型,只要实现了Stringer接口,就能够传递给fmt.Print函数,然后打印出该类型String()函数的返回值。
    package main
    import (
        "fmt"
        "strconv" //for conversions to and from string
    )
    
    type Human struct {  //定义结构体
        name string
        age int
        phone string
    }
    
    //Returns a nice string representing a Human
    //With this method, Human implements fmt.Stringer
    func (h Human) String() string {  //实现 String()方法
        //We called strconv.Itoa on h.age to make a string out of it.
        //Also, thank you, UNICODE!
        return "❰"+h.name+" - "+strconv.Itoa(h.age)+" years -  ✆ " +h.phone+"❱"
    }
    
    func main() {
        Bob := Human{"Bob", 39, "000-7777-XXX"}
        fmt.Println("This Human is : ", Bob)   //fmt.Println函数接收实现了String接口的参数
    }
    
    //输出结果:
    This Human is : ❰Bob - 39 years - ✆ 000-7777-XXX❱
    

      参考:https://www.jianshu.com/p/dbd4e6b4900c

  • 相关阅读:
    MAVLINK协议
    rtt之通用bootloader
    easy flash &easy log
    电源适配器DC插头规格
    Jquery实现仿腾讯微薄的广播发表
    可供前端工程师选择的精彩CSS框架
    javascript实现记录文本框内文字个数
    Jquery仿IGoogle实现可拖动窗口(源码)
    jquery javascript 回到顶部功能
    常用的经典jquery代码[转]
  • 原文地址:https://www.cnblogs.com/wanghaijun999/p/8258614.html
Copyright © 2011-2022 走看看