Golang kindNoPointers标志详解

在看golang源码时,有时会判断变量类型是否为kindNoPointers,然后根据判断做出一些处理,那kindNoPointers究竟表示什么意思呢?

定义

@(src\runtime\typekind.go:37)

kindNoPointers  = 1 << 7

注,在源码中多个文件都有定义kindNoPointers,但没关系,值都是1 << 7

从字面上看,这个标志用来表示类型是否含有指针,事实上也确实如此,看源码:

@(src/cmd/compile/internal/gc/reflect.go:887)

func dcommontype(lsym *obj.LSym, t *types.Type) int {
	...
	if !types.Haspointers(t) {
		i |= objabi.KindNoPointers
	}
	...
}

编译器会对判断每个类型是否含有指针,没有就置KindNoPointers。具体判断是否含有指针代码如下:

@(src/cmd/compile/internal/types/type.go:887)

func Haspointers(t *Type) bool {
	return Haspointers1(t, false)
}

func Haspointers1(t *Type, ignoreNotInHeap bool) bool {
	switch t.Etype {
	case TINT, TUINT, TINT8, TUINT8, TINT16, TUINT16, TINT32, TUINT32, TINT64,
		TUINT64, TUINTPTR, TFLOAT32, TFLOAT64, TCOMPLEX64, TCOMPLEX128, TBOOL, TSSA:
		return false

	case TARRAY:
		if t.NumElem() == 0 { // empty array has no pointers
			return false
		}
		return Haspointers1(t.Elem(), ignoreNotInHeap)

	case TSTRUCT:
		for _, t1 := range t.Fields().Slice() {
			if Haspointers1(t1.Type, ignoreNotInHeap) {
				return true
			}
		}
		return false

	case TPTR, TSLICE:
		return !(ignoreNotInHeap && t.Elem().NotInHeap())

	case TTUPLE:
		ttup := t.Extra.(*Tuple)
		return Haspointers1(ttup.first, ignoreNotInHeap) || Haspointers1(ttup.second, ignoreNotInHeap)
	}

	return true
}

代码不多,可简单总结下:

  • 当类型为TINT, TUINT, TINT8, TUINT8, TINT16, TUINT16, TINT32, TUINT32, TINT64,TUINT64, TUINTPTR, TFLOAT32, TFLOAT64, TCOMPLEX64, TCOMPLEX128, TBOOL, TSSA时,kindNoPointers为true。
  • 当TARRAY、TSTRUCT里面的包含的类型都是kindNoPointers,则这个TARRAY、TSTRUCT为kindNoPointers。
  • 当类型为TPTR、TSLICE时,kindNoPointers为true。
  • 当类型为TTUPLE时,当tuple里面的两个元素都为kindNoPointers时,则tuple为kindNoPointers。

在Go里面好像没有看到过tuple类型,估计是内部用的,没有开放出来

猜你喜欢

转载自blog.csdn.net/fengshenyun/article/details/100712922
今日推荐