在Go语言中将类型转换为结构体类型。

huangapple go评论88阅读模式
英文:

casting to struct type in go lang

问题

我有一些以以下形式的C宏:

#define VARATT_IS_4B(PTR) \
    ((((varattrib_1b *) (PTR))->va_header & 0x80) == 0x00)

我想将其转换为Go语言。我正在尝试做如下操作:

func varAttIs1B(ptr uintptr) bool {
    return (*varAttrib1b(ptr).vaHeader & 0x01) == 0x01
}

但是,它不起作用,我得到了编译器错误**"cannot convert ptr (type int) to type varAttrib1b"**。

varAttrib1b是一个具有两个字段的结构体,ptr是一个uintptr(也可以是其他类型)。

type varAttrib1b struct {
    vaHeader uint8
    vaData   []string
}

我该如何解决这个问题?

英文:

I have some c macros in the form of

#define VARATT_IS_4B(PTR) \
	((((varattrib_1b *) (PTR))->va_header & 0x80) == 0x00)

and want to convert it to Go lang. I am doing something like

func varAttIs1B(ptr uintptr) bool {
	return (*varAttrib1b(ptr).vaHeader & 0x01) == 0x01
}

but yeah, it is not working and I am getting compiler error "cannot convert ptr (type int) to type varAttrib1b".

varAttrib1b is a struct with two fields and ptr is a uintptr(could be some other type also).

type varAttrib1b struct {
	vaHeader uint8
	vaData   []string
}

How can I do this?

答案1

得分: 4

在Go语言中,你不能将指针强制转换为任意类型。如果你真的想这样做,你应该使用unsafe.Pointer:

type varAttrib1b struct {
	vaHeader uint8
	vaData   []string
}

func varAttIs1B(ptr uintptr) bool {
	return ((*varAttrib1b)(unsafe.Pointer(ptr)).vaHeader & 0x01) == 0x01
}

这段代码可以编译并运行,但你确定在Go语言中没有更安全的方法吗?你不能只是定义一个接口吗?

type Attr interface {
    AttrIs1B() bool
}

func (b varAttrib1b) AttrIs1B() bool {
    return b.vaHeader & 0x01 == 0x01
}

func varAttIs1B(attr Attr) bool {
	return attr.AttrIs1B()
}

或者使用类型断言来实现呢?

func varAttIs1B(ptr interface{}) bool {
    switch a := ptr.(type) {
    case varAttrib1b:
		return a.vaHeader & 0x01 == 0x01
    }
	return false
}

希望这些代码对你有帮助!

英文:

You cannot cast pointers to arbitrary types in Go. If you really want to do that, you should use unsafe.Pointer:

<!-- language: go -->

type varAttrib1b struct {
	vaHeader uint8
	vaData   []string
}

func varAttIs1B(ptr uintptr) bool {
	return ((*varAttrib1b)(unsafe.Pointer(ptr)).vaHeader &amp; 0x01) == 0x01
}

It compiles and works, but are you sure there is no safe way of doing that in go? Can't you just define an interface:

<!-- language: go -->

type Attr interface {
    AttrIs1B() bool
}

func (b varAttrib1b) AttrIs1B() bool {
    return b.vaHeader &amp; 0x01 == 0x01
}

func varAttIs1B(attr Attr) bool {
	return attr.AttrIs1B()
}

Or implement it with type casts?

<!-- language: go -->

func varAttIs1B(ptr interface{}) bool {
    switch a := ptr.(type) {
    case varAttrib1b:
		return a.vaHeader &amp; 0x01 == 0x01
    }
	return false
}

huangapple
  • 本文由 发表于 2015年5月17日 21:12:35
  • 转载请务必保留本文链接:https://go.coder-hub.com/30287218.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定