如何处理来自数据库的 nil 返回值?

我正在编写一个基本程序来从数据库表中读取值并在表中打印。该表由一个古老的程序填充。该行中的某些字段是可选的,当我尝试将它们作为字符串读取时,出现以下错误:

panic: sql: Scan error on column index 2: unsupported driver -> Scan pair: <nil> -> *string

在我阅读了类似问题的其他问题后,我想出了以下代码来处理 nil 值。该方法在实践中效果很好。我得到纯文本和空字符串的值而不是 nil 值。

但是,我有两个顾虑:

  1. 这看起来效率不高。我需要像这样处理 25 个以上的字段,这意味着我将每个字段作为字节读取并转换为字符串。太多的函数调用和转换。两个结构体来处理数据等等...

  2. 代码看起来很丑。它已经看起来很复杂,有 2 个字段,并且在我 25+ 时变得不可读

我做错了吗?有没有更好/更干净/更高效/惯用的 golang 方式来从数据库中读取值?

我发现很难相信像 Go 这样的现代语言不会优雅地处理数据库返回。

提前致谢!

代码片段:


// DB read format

type udInfoBytes struct {

  id                     []byte

  state                  []byte

}


// output format

type udInfo struct {

  id                     string

  state                  string

}


func CToGoString(c []byte) string {

  n := -1

  for i, b := range c {

    if b == 0 {

      break

    }

    n = i

  }

  return string(c[:n+1])

}


func dbBytesToString(in udInfoBytes) udInfo {


  var out udInfo

  var s string

  var t int


  out.id = CToGoString(in.id)

  out.state = stateName(in.state)

  return out

}


func GetInfo(ud string) udInfo {


  db := getFileHandle()

  q := fmt.Sprintf("SELECT id,state FROM Mytable WHERE id='%s' ", ud)


  rows, err := db.Query(q)

  if err != nil {

    log.Fatal(err)

  }

  defer rows.Close()

  ret := udInfo{}

  r := udInfoBytes{}

  for rows.Next() {

    err := rows.Scan(&r.id, &r.state)


    if err != nil {

      log.Println(err)

    }

    break

  }

  err = rows.Err()

  if err != nil {

    log.Fatal(err)

  }


  ret = dbBytesToString(r)

  defer db.Close()

  return ret

}



梦里花落0921
浏览 177回答 3
3回答

翻过高山走不出你

有不同的类型来处理null值从数据库中,如来sql.NullBool,sql.NullFloat64等等。例如:&nbsp;var s sql.NullString&nbsp;err := db.QueryRow("SELECT name FROM foo WHERE id=?", id).Scan(&s)&nbsp;...&nbsp;if s.Valid {&nbsp; &nbsp; // use s.String&nbsp;} else {&nbsp; &nbsp; // NULL value&nbsp;}

慕的地8271018

另一种解决方案是使用 COALESCE 函数在 SQL 语句本身中处理此问题(尽管并非所有 DB 都可能支持此功能)。例如,您可以改为使用:q&nbsp;:=&nbsp;fmt.Sprintf("SELECT&nbsp;id,COALESCE(state,&nbsp;'')&nbsp;as&nbsp;state&nbsp;FROM&nbsp;Mytable&nbsp;WHERE&nbsp;id='%s'&nbsp;",&nbsp;ud)如果它在数据库中存储为 NULL,这将有效地为 'state' 提供一个空字符串的默认值。
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go