Skip to content

Precision Issue with SQL Server real Type in Golang Resulting in Unexpected Floating-Point Value #802

@littlestar1998

Description

@littlestar1998

I have encountered a problem where my data field is of the real type and has a value of 1.232, leading to precision issues. The code is as follows:

Create SQL:

create table dbo.test
(
    id     int,
    v_real real
)
go

INSERT INTO master.dbo.test (id, v_real) VALUES (1, 1.232);

golang code

package main

import (
	"context"
	"database/sql"
	"fmt"
	_ "github.com/denisenkom/go-mssqldb"
	"log"
)

func main() {

	db, err := sql.Open("sqlserver", "sqlserver://sa:YourStrongPassw0rd@192.168.31.40:1433?database=master&connection+timeout=30")
	if err != nil {
		log.Fatal("Error creating connection pool: ", err.Error())
	}
	defer db.Close()

	err = db.PingContext(context.Background())
	if err != nil {
		log.Fatal("Error pinging database: ", err.Error())
	}
	fmt.Println("Connected to the database successfully")

	query := "SELECT id,v_real FROM dbo.test"
	rows, err := db.QueryContext(context.Background(), query)
	if err != nil {
		log.Fatal("Error querying database: ", err.Error())
	}
	defer rows.Close()

	// 获取列的信息
	columns, err := rows.Columns()
	if err != nil {
		log.Fatal("Error getting columns: ", err.Error())
	}

	values := make([]interface{}, len(columns))
	valuePtrs := make([]interface{}, len(columns))
	for i := range columns {
		valuePtrs[i] = &values[i]
	}

	// 读取行数据
	for rows.Next() {
		err := rows.Scan(valuePtrs...)
		if err != nil {
			log.Fatal("Error scanning row: ", err.Error())
		}

		for i, col := range columns {
			fmt.Printf("%s: %v\n", col, values[i])
		}
	}
}

The execution result is:

id: 1
v_real: 1.2319999933242798

The main issue arises from the type conversion in types.go at line 396. The math.Float32frombits function returns a 32-bit number, which is then forcibly converted to 64-bit.

Here is a Golang example:

var v float32 = 1.232
fmt.Println(fmt.Sprintln("%+v", float64(v)))

Problem reproduction:

If necessary, I can submit a PR to fix this.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions