一、interface简介

interface(接口)是golang最重要的特性之一,Interface类型可以定义一组方法,但是这些不需要实现。并且interface不能包含任何变量。

简单的说:

  • interface是方法的集合
  • interface是一种类型,并且是指针类型
  • interface的更重要的作用在于多态实现

interface定义

  1. type 接口名称 interface {
  2. method1 (参数列表) 返回值列表
  3. method2 (参数列表) 返回值列表
  4. ...
  5. }

interface使用

  • 接口的使用不仅仅针对结构体,自定义类型、变量等等都可以实现接口。
  • 如果一个接口没有任何方法,我们称为空接口,由于空接口没有方法,所以任何类型都实现了空接口。
  • 要实现一个接口,必须实现该接口里面的所有方法。
  1. package main
  2.  
  3. import "fmt"
  4.  
  5. //定义接口
  6. type Skills interface {
  7. Running()
  8. Getname() string
  9.  
  10. }
  11.  
  12. type Student struct {
  13. Name string
  14. Age int
  15. }
  16.  
  17. // 实现接口
  18. func (p Student) Getname() string{ //实现Getname方法
  19. fmt.Println(p.Name )
  20. return p.Name
  21. }
  22.  
  23. func (p Student) Running() { // 实现 Running方法
  24. fmt.Printf("%s running",p.Name)
  25. }
  26. func main() {
  27. var skill Skills
  28. var stu1 Student
  29. stu1.Name = "wd"
  30. stu1.Age =
  31. skill = stu1
  32. skill.Running() //调用接口
  33. }
  34.  
  35. //wd running

多态

上面提到了,go语言中interface是实现多态的一种形式,所谓多态,就是一种事物的多种形态,与python中类的多态是一致的。

同一个interface,不同的类型实现,都可以进行调用,它们都按照统一接口进行操作。

在上面的示例中,我们增加一个Teacher结构体,同样实现接口进行说明:

  1. package main
  2.  
  3. import "fmt"
  4.  
  5. type Skills interface {
  6. Running()
  7. Getname() string
  8.  
  9. }
  10.  
  11. type Student struct {
  12. Name string
  13. Age int
  14. }
  15.  
  16. type Teacher struct {
  17. Name string
  18. Salary int
  19. }
  20.  
  21. func (p Student) Getname() string{ //实现Getname方法
  22. fmt.Println(p.Name )
  23. return p.Name
  24. }
  25.  
  26. func (p Student) Running() { // 实现 Running方法
  27. fmt.Printf("%s running",p.Name)
  28. }
  29.  
  30. func (p Teacher) Getname() string{ //实现Getname方法
  31. fmt.Println(p.Name )
  32. return p.Name
  33. }
  34.  
  35. func (p Teacher) Running() { // 实现 Running方法
  36. fmt.Printf("\n%s running",p.Name)
  37. }
  38. func main() {
  39. var skill Skills
  40. var stu1 Student
  41. var t1 Teacher
  42. t1.Name = "wang"
  43. stu1.Name = "wd"
  44. stu1.Age =
  45. skill = stu1
  46. skill.Running()
  47. skill = t1
  48. t1.Running()
  49. }
  50. //wd running
  51. //wang running

接口嵌套

go语言中的接口可以嵌套,可以理解我继承,子接口拥有父接口的所有方法,并且想要使用该子接口的话,必须将父接口和子接口的所有方法都实现。

  1. type Skills interface {
  2. Running()
  3. Getname() string
  4.  
  5. }
  6.  
  7. type Test interface {
  8. sleeping()
  9. Skills //继承Skills
  10. }

类型转换

由于接口是一般类型,当我们使用接口时候可能不知道它是那个类型实现的,基本数据类型我们有对应的方法进行类型转换,当然接口类型也有类型转换。

当然我们也可以用这个方式来进行类型的判断。

转换方式:

  1. var s int
  2. var x interface
  3.  
  4. x = s
  5. y , ok := x.(int) //将interface 转为int,ok可省略 但是省略以后转换失败会报错,true转换成功,false转换失败, 并采用默认值

示例:

  1. package main
  2.  
  3. import "fmt"
  4.  
  5. func main() {
  6. var x interface{}
  7.  
  8. s := "WD"
  9. x = s
  10. y,ok := x.(int)
  11. z,ok1 := x.(string)
  12. fmt.Println(y,ok)
  13. fmt.Println(z,ok1)
  14. }
  15. //0 false
  16. //WD true

判断类型示例:

  1. package main
  2.  
  3. import "fmt"
  4.  
  5. type Student struct {
  6. Name string
  7. }
  8.  
  9. func TestType(items ...interface{}) {
  10. for k, v := range items {
  11. switch v.(type) {
  12. case string:
  13. fmt.Printf("type is string, %d[%v]\n", k, v)
  14. case bool:
  15. fmt.Printf("type is bool, %d[%v]\n", k, v)
  16. case int:
  17. fmt.Printf("type is int, %d[%v]\n", k, v)
  18. case float32, float64:
  19. fmt.Printf("type is float, %d[%v]\n", k, v)
  20. case Student:
  21. fmt.Printf("type is Student, %d[%v]\n", k, v)
  22. case *Student:
  23. fmt.Printf("type is Student, %d[%p]\n", k, v)
  24. }
  25. }
  26. }
  27.  
  28. func main() {
  29. var stu Student
  30. TestType("WD", , stu,3.3)
  31. }
  32. //type is string, 0[WD]
  33. //type is int, 1[100]
  34. //type is Student, 2[{}]
  35. //type is float, 3[3.3]

二、反射reflect

反射是程序执行时检查其所拥有的结构。尤其是类型的一种能力。这是元编程的一种形式。它同一时候也是造成混淆的重要来源。

每一个语言的反射模型都不同(同一时候很多语言根本不支持反射,python通过hasattr方法实现)

go语言中的反射通过refect包实现,reflect包实现了运行时反射,允许程序操作任意类型的对象。

在介绍反射之前先说明下reflect包中的两个数据类Type和Value。

Type

Type:Type类型用来表示一个go类型。

不是所有go类型的Type值都能使用所有方法。请参见每个方法的文档获取使用限制。在调用有分类限定的方法时,应先使用Kind方法获知类型的分类。调用该分类不支持的方法会导致运行时的panic。

获取Type对象的方法:

  1. func TypeOf(i interface{}) Type

示例:

  1. package main
  2.  
  3. import (
  4. "reflect"
  5. "fmt"
  6. )
  7.  
  8. func main() {
  9. str := "wd"
  10. res_type := reflect.TypeOf(str)
  11. fmt.Println(res_type) //string
  12. }

reflect.Type中方法

通用方法:

  1. // 通用方法
  2.  
  3. func (t *rtype) String() string // 获取 t 类型的字符串描述,不要通过 String 来判断两种类型是否一致。
  4.  
  5. func (t *rtype) Name() string // 获取 t 类型在其包中定义的名称,未命名类型则返回空字符串。
  6.  
  7. func (t *rtype) PkgPath() string // 获取 t 类型所在包的名称,未命名类型则返回空字符串。
  8.  
  9. func (t *rtype) Kind() reflect.Kind // 获取 t 类型的类别。
  10.  
  11. func (t *rtype) Size() uintptr // 获取 t 类型的值在分配内存时的大小,功能和 unsafe.SizeOf 一样。
  12.  
  13. func (t *rtype) Align() int // 获取 t 类型的值在分配内存时的字节对齐值。
  14.  
  15. func (t *rtype) FieldAlign() int // 获取 t 类型的值作为结构体字段时的字节对齐值。
  16.  
  17. func (t *rtype) NumMethod() int // 获取 t 类型的方法数量。
  18.  
  19. func (t *rtype) Method() reflect.Method // 根据索引获取 t 类型的方法,如果方法不存在,则 panic。
  20. // 如果 t 是一个实际的类型,则返回值的 Type 和 Func 字段会列出接收者。
  21. // 如果 t 只是一个接口,则返回值的 Type 不列出接收者,Func 为空值。
  22.  
  23. func (t *rtype) MethodByName(string) (reflect.Method, bool) // 根据名称获取 t 类型的方法。
  24.  
  25. func (t *rtype) Implements(u reflect.Type) bool // 判断 t 类型是否实现了 u 接口。
  26.  
  27. func (t *rtype) ConvertibleTo(u reflect.Type) bool // 判断 t 类型的值可否转换为 u 类型。
  28.  
  29. func (t *rtype) AssignableTo(u reflect.Type) bool // 判断 t 类型的值可否赋值给 u 类型。
  30.  
  31. func (t *rtype) Comparable() bool // 判断 t 类型的值可否进行比较操作
  1.  
  1. ####注意对于:数组、切片、映射、通道、指针、接口
  2. func (t *rtype) Elem() reflect.Type // 获取元素类型、获取指针所指对象类型,获取接口的动态类型

示例:

  1. package main
  2.  
  3. import (
  4. "fmt"
  5. "reflect"
  6. )
  7.  
  8. type Skills interface {
  9. reading()
  10. running()
  11. }
  12.  
  13. type Student struct {
  14. Name string
  15. Age int
  16.  
  17. }
  18.  
  19. func (self Student) runing(){
  20. fmt.Printf("%s is running\n",self.Name)
  21. }
  22. func (self Student) reading(){
  23. fmt.Printf("%s is reading\n" ,self.Name)
  24. }
  25. func main() {
  26. stu1 := Student{Name:"wd",Age:}
  27. inf := new(Skills)
  28. stu_type := reflect.TypeOf(stu1)
  29. inf_type := reflect.TypeOf(inf).Elem() // 特别说明,引用类型需要用Elem()获取指针所指的对象类型
  30. fmt.Println(stu_type.String()) //main.Student
  31. fmt.Println(stu_type.Name()) //Student
  32. fmt.Println(stu_type.PkgPath()) //main
  33. fmt.Println(stu_type.Kind()) //struct
  34. fmt.Println(stu_type.Size()) //
  35. fmt.Println(inf_type.NumMethod()) //
  36. fmt.Println(inf_type.Method(),inf_type.Method().Name) // {reading main func() <invalid Value> 0} reading
  37. fmt.Println(inf_type.MethodByName("reading")) //{reading main func() <invalid Value> 0} true
  38.  
  39. }

其他方法:

  1. // 数值
  2.  
  3. func (t *rtype) Bits() int // 获取数值类型的位宽,t 必须是整型、浮点型、复数型
  4.  
  5. ------------------------------
  6.  
  7. // 数组
  8.  
  9. func (t *rtype) Len() int // 获取数组的元素个数
  10.  
  11. ------------------------------
  12.  
  13. // 映射
  14.  
  15. func (t *rtype) Key() reflect.Type // 获取映射的键类型
  16.  
  17. ------------------------------
  18.  
  19. // 通道
  20.  
  21. func (t *rtype) ChanDir() reflect.ChanDir // 获取通道的方向
  22.  
  23. ------------------------------
  24.  
  25. // 结构体
  26.  
  27. func (t *rtype) NumField() int // 获取字段数量
  28.  
  29. func (t *rtype) Field(int) reflect.StructField // 根据索引获取字段
  30.  
  31. func (t *rtype) FieldByName(string) (reflect.StructField, bool) // 根据名称获取字段
  32.  
  33. func (t *rtype) FieldByNameFunc(match func(string) bool) (reflect.StructField, bool) // 根据指定的匹配函数 math 获取字段
  34.  
  35. func (t *rtype) FieldByIndex(index []int) reflect.StructField // 根据索引链获取嵌套字段
  36.  
  37. ------------------------------
  38.  
  39. // 函数
  40.  
  41. func (t *rtype) NumIn() int // 获取函数的参数数量
  42.  
  43. func (t *rtype) In(int) reflect.Type // 根据索引获取函数的参数信息
  44.  
  45. func (t *rtype) NumOut() int // 获取函数的返回值数量
  46.  
  47. func (t *rtype) Out(int) reflect.Type // 根据索引获取函数的返回值信息
  48.  
  49. func (t *rtype) IsVariadic() bool // 判断函数是否具有可变参数。
  50. // 如果有可变参数,则 t.In(t.NumIn()-1) 将返回一个切片。

示例:

  1. package main
  2.  
  3. import (
  4. "fmt"
  5. "reflect"
  6. )
  7.  
  8. type Skills interface {
  9. reading()
  10. running()
  11. }
  12.  
  13. type Student struct {
  14. Name string
  15. Age int
  16.  
  17. }
  18.  
  19. func (self Student) runing(){
  20. fmt.Printf("%s is running\n",self.Name)
  21. }
  22. func (self Student) reading(){
  23. fmt.Printf("%s is reading\n" ,self.Name)
  24. }
  25. func main() {
  26. stu1 := Student{Name:"wd",Age:}
  27. stu_type := reflect.TypeOf(stu1)
  28. fmt.Println(stu_type.NumField()) //
  29. fmt.Println(stu_type.Field()) //{Name string 0 [0] false}
  30. fmt.Println(stu_type.FieldByName("Age")) //{{Age int 16 [1] false} true
  31. }

Value

不是所有go类型值的Value表示都能使用所有方法。请参见每个方法的文档获取使用限制。在调用有分类限定的方法时,应先使用Kind方法获知该值的分类。调用该分类不支持的方法会导致运行时的panic。

Value为go值提供了反射接口,获取Value对象方法:

  1. func ValueOf(i interface{}) Value

示例:

  1. str := "wd"
  2. val := reflect.ValueOf(str)
  3. //wd

reflect.Value方法

注意:以下所有方法中的v是reflect.Value返回的值。

reflect.Value.Kind():获取变量类别,返回常量

  1. const (
  2. Invalid Kind = iota
  3. Bool
  4. Int
  5. Int8
  6. Int16
  7. Int32
  8. Int64
  9. Uint
  10. Uint8
  11. Uint16
  12. Uint32
  13. Uint64
  14. Uintptr
  15. Float32
  16. Float64
  17. Complex64
  18. Complex128
  19. Array
  20. Chan
  21. Func
  22. Interface
  23. Map
  24. Ptr
  25. Slice
  26. String
  27. Struct
  28. UnsafePointer
  29. )

常量类型

  1. package main
  2.  
  3. import (
  4. "reflect"
  5. "fmt"
  6. )
  7.  
  8. func main() {
  9. str := "wd"
  10. val := reflect.ValueOf(str).Kind()
  11. fmt.Println(val)//string
  12. }

用于获取值方法:

  1. func (v Value) Int() int64 // 获取int类型值,如果 v 值不是有符号整型,则 panic。
  2.  
  3. func (v Value) Uint() uint64 // 获取unit类型的值,如果 v 值不是无符号整型(包括 uintptr),则 panic。
  4.  
  5. func (v Value) Float() float64 // 获取float类型的值,如果 v 值不是浮点型,则 panic。
  6.  
  7. func (v Value) Complex() complex128 // 获取复数类型的值,如果 v 值不是复数型,则 panic。
  8.  
  9. func (v Value) Bool() bool // 获取布尔类型的值,如果 v 值不是布尔型,则 panic。
  10.  
  11. func (v Value) Len() int // 获取 v 值的长度,v 值必须是字符串、数组、切片、映射、通道。
  12.  
  13. func (v Value) Cap() int // 获取 v 值的容量,v 值必须是数值、切片、通道。
  14.  
  15. func (v Value) Index(i int) reflect.Value // 获取 v 值的第 i 个元素,v 值必须是字符串、数组、切片,i 不能超出范围。
  16.  
  17. func (v Value) Bytes() []byte // 获取字节类型的值,如果 v 值不是字节切片,则 panic。
  18.  
  19. func (v Value) Slice(i, j int) reflect.Value // 获取 v 值的切片,切片长度 = j - i,切片容量 = v.Cap() - i。
  20. // v 必须是字符串、数值、切片,如果是数组则必须可寻址。i 不能超出范围。
  21.  
  22. func (v Value) Slice3(i, j, k int) reflect.Value // 获取 v 值的切片,切片长度 = j - i,切片容量 = k - i。
  23. // i、j、k 不能超出 v 的容量。i <= j <= k。
  24. // v 必须是字符串、数值、切片,如果是数组则必须可寻址。i 不能超出范围。
  25.  
  26. func (v Value) MapIndex(key Value) reflect.Value // 根据 key 键获取 v 值的内容,v 值必须是映射。
  27. // 如果指定的元素不存在,或 v 值是未初始化的映射,则返回零值(reflect.ValueOf(nil))
  28.  
  29. func (v Value) MapKeys() []reflect.Value // 获取 v 值的所有键的无序列表,v 值必须是映射。
  30. // 如果 v 值是未初始化的映射,则返回空列表。
  31.  
  32. func (v Value) OverflowInt(x int64) bool // 判断 x 是否超出 v 值的取值范围,v 值必须是有符号整型。
  33.  
  34. func (v Value) OverflowUint(x uint64) bool // 判断 x 是否超出 v 值的取值范围,v 值必须是无符号整型。
  35.  
  36. func (v Value) OverflowFloat(x float64) bool // 判断 x 是否超出 v 值的取值范围,v 值必须是浮点型。
  37.  
  38. func (v Value) OverflowComplex(x complex128) bool // 判断 x 是否超出 v 值的取值范围,v 值必须是复数型。

设置值方法:

  1. func (v Value) SetInt(x int64) //设置int类型的值
  2.  
  3. func (v Value) SetUint(x uint64) // 设置无符号整型的值
  4.  
  5. func (v Value) SetFloat(x float64) // 设置浮点类型的值
  6.  
  7. func (v Value) SetComplex(x complex128) //设置复数类型的值
  8.  
  9. func (v Value) SetBool(x bool) //设置布尔类型的值
  10.  
  11. func (v Value) SetString(x string) //设置字符串类型的值
  12.  
  13. func (v Value) SetLen(n int) // 设置切片的长度,n 不能超出范围,不能为负数。
  14.  
  15. func (v Value) SetCap(n int) //设置切片的容量
  16.  
  17. func (v Value) SetBytes(x []byte) //设置字节类型的值
  18.  
  19. func (v Value) SetMapIndex(key, val reflect.Value) //设置map的key和value,前提必须是初始化以后,存在覆盖、不存在添加

其他方法:

  1. ##########结构体相关:
  2. func (v Value) NumField() int // 获取结构体字段(成员)数量
  3.  
  4. func (v Value) Field(i int) reflect.Value //根据索引获取结构体字段
  5.  
  6. func (v Value) FieldByIndex(index []int) reflect.Value // 根据索引链获取结构体嵌套字段
  7.  
  8. func (v Value) FieldByName(string) reflect.Value // 根据名称获取结构体的字段,不存在返回reflect.ValueOf(nil)
  9.  
  10. func (v Value) FieldByNameFunc(match func(string) bool) Value // 根据匹配函数 match 获取字段,如果没有匹配的字段,则返回零值(reflect.ValueOf(nil))
  11.  
  12. ########通道相关:
  13. func (v Value) Send(x reflect.Value)// 发送数据(会阻塞),v 值必须是可写通道。
  14.  
  15. func (v Value) Recv() (x reflect.Value, ok bool) // 接收数据(会阻塞),v 值必须是可读通道。
  16.  
  17. func (v Value) TrySend(x reflect.Value) bool // 尝试发送数据(不会阻塞),v 值必须是可写通道。
  18.  
  19. func (v Value) TryRecv() (x reflect.Value, ok bool) // 尝试接收数据(不会阻塞),v 值必须是可读通道。
  20.  
  21. func (v Value) Close() // 关闭通道
  22.  
  23. ########函数相关
  24. func (v Value) Call(in []Value) (r []Value) // 通过参数列表 in 调用 v 值所代表的函数(或方法)。函数的返回值存入 r 中返回。
  25. // 要传入多少参数就在 in 中存入多少元素。
  26. // Call 即可以调用定参函数(参数数量固定),也可以调用变参函数(参数数量可变)。
  27.  
  28. func (v Value) CallSlice(in []Value) []Value // 调用变参函数

示例一:获取和设置普通类型的值

  1. package main
  2.  
  3. import (
  4. "reflect"
  5. "fmt"
  6. )
  7.  
  8. func main() {
  9. str := "wd"
  10. age :=
  11. fmt.Println(reflect.ValueOf(str).String()) //获取str的值,结果wd
  12. fmt.Println(reflect.ValueOf(age).Int()) //获取age的值,结果age
  13. str2 := reflect.ValueOf(&str) //获取Value类型
  14. str2.Elem().SetString("jack") //设置值
  15. fmt.Println(str2.Elem(),age) //jack 11
  16. }

示例二:简单结构体操作

  1. package main
  2.  
  3. import (
  4. "fmt"
  5. "reflect"
  6. )
  7.  
  8. type Skills interface {
  9. reading()
  10. running()
  11. }
  12.  
  13. type Student struct {
  14. Name string
  15. Age int
  16.  
  17. }
  18.  
  19. func (self Student) runing(){
  20. fmt.Printf("%s is running\n",self.Name)
  21. }
  22. func (self Student) reading(){
  23. fmt.Printf("%s is reading\n" ,self.Name)
  24. }
  25. func main() {
  26. stu1 := Student{Name:"wd",Age:}
  27. stu_val := reflect.ValueOf(stu1) //获取Value类型
  28. fmt.Println(stu_val.NumField()) //
  29. fmt.Println(stu_val.Field(),stu_val.Field()) //wd 22
  30. fmt.Println(stu_val.FieldByName("Age")) //
  31. stu_val2 := reflect.ValueOf(&stu1).Elem()
  32. stu_val2.FieldByName("Age").SetInt() //设置字段值 ,结果33
  33. fmt.Println(stu1.Age)
  34.  
  35. }

示例三:通过反射调用结构体中的方法,通过reflect.Value.Method(i int).Call()或者reflect.Value.MethodByName(name string).Call()实现

  1. package main
  2.  
  3. import (
  4. "fmt"
  5. "reflect"
  6. )
  7.  
  8. type Student struct {
  9. Name string
  10. Age int
  11. }
  12.  
  13. func (this *Student) SetName(name string) {
  14. this.Name = name
  15. fmt.Printf("set name %s\n",this.Name )
  16. }
  17.  
  18. func (this *Student) SetAge(age int) {
  19. this.Age = age
  20. fmt.Printf("set age %d\n",age )
  21. }
  22.  
  23. func (this *Student) String() string {
  24. fmt.Printf("this is %s\n",this.Name)
  25. return this.Name
  26. }
  27.  
  28. func main() {
  29. stu1 := &Student{Name:"wd",Age:}
  30. val := reflect.ValueOf(stu1) //获取Value类型,也可以使用reflect.ValueOf(&stu1).Elem()
  31. val.MethodByName("String").Call(nil) //调用String方法
  32.  
  33. params := make([]reflect.Value, )
  34. params[] = reflect.ValueOf()
  35. val.MethodByName("SetAge").Call(params) //通过名称调用方法
  36.  
  37. params[] = reflect.ValueOf("jack")
  38. val.Method().Call(params) //通过方法索引调用
  39.  
  40. fmt.Println(stu1.Name,stu1.Age)
  41. }
  42. //this is wd
  43. //set age 18
  44. //set name jack
  45. //jack 18

go语言之行--接口(interface)、反射(reflect)详解的更多相关文章

  1. Go语言学习笔记(四)结构体struct & 接口Interface & 反射reflect

    加 Golang学习 QQ群共同学习进步成家立业工作 ^-^ 群号:96933959 结构体struct struct 用来自定义复杂数据结构,可以包含多个字段(属性),可以嵌套: go中的struc ...

  2. golang中的反射reflect详解

    先重复一遍反射三定律: 1.反射可以将"接口类型变量"转换为"反射类型对象". 2.反射可以将"反射类型对象"转换为"接口类型变量 ...

  3. 【python3+request】python3+requests接口自动化测试框架实例详解教程

    转自:https://my.oschina.net/u/3041656/blog/820023 [python3+request]python3+requests接口自动化测试框架实例详解教程 前段时 ...

  4. python+requests接口自动化测试框架实例详解

    python+requests接口自动化测试框架实例详解   转自https://my.oschina.net/u/3041656/blog/820023 摘要: python + requests实 ...

  5. Java 反射机制详解(上)

    一.什么是反射 JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意方法和属性:这种动态获取信息以及动态调用对象方法的功能称为java ...

  6. Java 反射机制详解(下)

    续:Java 反射机制详解(上) 三.怎么使用反射 想要使用反射机制,就必须要先获取到该类的字节码文件对象(.class),通过字节码文件对象,就能够通过该类中的方法获取到我们想要的所有信息(方法,属 ...

  7. ubuntu 下命令行播放器mplayer 使用详解

    ubuntu 下命令行播放器mplayer 使用详解 2011-01-02 21:00:42|  分类: Linux/Unix |  标签: |字号大中小 订阅 使用 MPlayer 播放媒体文件最简 ...

  8. C语言对文件的操作函数用法详解1

    在ANSIC中,对文件的操作分为两种方式,即: 流式文件操作 I/O文件操作 一.流式文件操作 这种方式的文件操作有一个重要的结构FILE,FILE在stdio.h中定义如下: typedef str ...

  9. “全栈2019”Java第六十五章:接口与默认方法详解

    难度 初级 学习时间 10分钟 适合人群 零基础 开发语言 Java 开发环境 JDK v11 IntelliJ IDEA v2018.3 文章原文链接 "全栈2019"Java第 ...

随机推荐

  1. Git免输入密码提交

    1.首先你需要下载 http://files.cnblogs.com/files/zhanqun/putty.7z 文件夹内包含下面这些文件:

  2. 如何通过活字格实现Excel 汇总

    企业中,经常面临需要汇总大批量的Excel 数据表的需求.如果仅通过手工汇总,则会有非常大的工作量,而且还很容易出现错误.此时,如果可以借助活字格这样的工具,来帮助实现汇总Excel 的功能,则会使工 ...

  3. XQuery使用sum求和,提示char不能转换为money解决方法

    select axml.value('sum(/root/pro/price)','money') 以上代码提示‘char不能转换为money’的错误,发现值为'0.0E0'.改为: select a ...

  4. Swagger使用教程 SwashbuckleEx

    一.前言 自从之前写了一篇<Webapi文档描述-swagger优化>这篇文章后,欠了大家一篇使用文档的说明,现在给大家补上哈. 二.环境 .Net Framework 4.5 WebAp ...

  5. windows下搭建Consul分布式系统和集群

    随着大数据时代的到来,分布式是解决大数据问题的一个主要手段,随着越来越多的分布式的服务,如何在分布式的系统中对这些服务做协调变成了一个很棘手的问题.我们在一个项目上注册了很多服务,在进行运维时,需要时 ...

  6. python爬虫_入门_翻页

    写出来的爬虫,肯定不能只在一个页面爬,只要要爬几个页面,甚至一个网站,这时候就需要用到翻页了 其实翻页很简单,还是这个页面http://bbs.fengniao.com/forum/10384633. ...

  7. UNIX高级环境编程(15)进程和内存分配 < 故宫角楼 >

    故宫角楼是很多摄影爱好者常去的地方,夕阳余辉下的故宫角楼平静而安详.   首先,了解一下进程的基本概念,进程在内存中布局和内容. 此外,还需要知道运行时是如何为动态数据结构(如链表和二叉树)分配额外内 ...

  8. EF5.0中的跨数据库操作

    以前在用MVC + EF 的项目中,都是一个数据库,一个DbContext,因此一直没有考虑过在MVC+EF的环境下对于多个数据库的操作问题.等到要使用时,才发现这个问题也不小(关键是有个坑).直接说 ...

  9. SVN 远程访问

    第一种方法 https://www.cnblogs.com/Leo_wl/p/3475167.html#_label0 默认协议为:https 端口号:443 服务器地址:https://主机名/sv ...

  10. Pre标签 自动换行

    <pre> 元素可定义预格式化的文本.被包围在 pre 元素中的文本通常会保留空格和换行符.而文本也会呈现为等宽字体. <pre> 标签的一个常见应用就是用来表示计算机的源代码 ...