有没有一种在Go语言中使用unsafe.Pointer实现整数转换函数的方法?

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

Is there a way to implement this integer casting function with unsafe Pointer in golang?

问题

我在想是否可以实现一个更简洁的函数版本,并且性能更好会很棒。

  1. func AnyIntToInt(x interface{}) (int, error) {
  2. switch val := x.(type) {
  3. case int8:
  4. return int(val), nil
  5. case int16:
  6. return int(val), nil
  7. case int32:
  8. return int(val), nil
  9. case int64:
  10. return int(val), nil
  11. case uint8:
  12. return int(val), nil
  13. case uint16:
  14. return int(val), nil
  15. case uint32:
  16. return int(val), nil
  17. case uint64:
  18. return int(val), nil
  19. }
  20. return 0, ErrNotInteger
  21. }

我尝试了下面这个版本,但是它产生了意外的结果。

  1. func AnyIntToInt(x interface{}) (int, error) {
  2. return *(*int)(unsafe.Pointer(&x))
  3. }
英文:

I was wondering if I could implement a less verbose version of this function. It would be great if it had better performance.

  1. func AnyIntToInt(x interface{}) (int, error) {
  2. switch val := x.(type) {
  3. case int8:
  4. return int(val), nil
  5. case int16:
  6. return int(val), nil
  7. case int32:
  8. return int(val), nil
  9. case int64:
  10. return int(val), nil
  11. case uint8:
  12. return int(val), nil
  13. case uint16:
  14. return int(val), nil
  15. case uint32:
  16. return int(val), nil
  17. case uint64:
  18. return int(val), nil
  19. }
  20. return 0, ErrNotInteger
  21. }

I have been trying with this one, however it yields unexpected results.

  1. func AnyIntToInt(x interface{}) (int, error) {
  2. return *(*int)(unsafe.Pointer(&x))
  3. }

答案1

得分: 1

问题中的代码是正确的方法,但是你可以使用reflect包来减少代码行数:

  1. func AnyIntToInt(x interface{}) (int, error) {
  2. v := reflect.ValueOf(x)
  3. switch v.Kind() {
  4. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  5. return int(v.Int()), nil
  6. case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
  7. return int(v.Uint()), nil
  8. }
  9. return 0, ErrNotInteger
  10. }

https://go.dev/play/p/gJ4ASo7AeyN

英文:

The code in the question is the way to go, but you can reduce lines of code using the reflect package:

  1. func AnyIntToInt(x interface{}) (int, error) {
  2. v := reflect.ValueOf(x)
  3. switch v.Kind() {
  4. case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
  5. return int(v.Int()), nil
  6. case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
  7. return int(v.Uint()), nil
  8. }
  9. return 0, ErrNotInteger
  10. }

https://go.dev/play/p/gJ4ASo7AeyN

huangapple
  • 本文由 发表于 2021年12月12日 08:08:10
  • 转载请务必保留本文链接:https://go.coder-hub.com/70319995.html
匿名

发表评论

匿名网友

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

确定