Strconv package

strconv package提供了很多字符串与其它类型转换的函数.

一个常用的要求是将一个字符串表示的真假值,转换为bool。 可以通过strcov.ParseBool()函数

for _, truth := range []string{"1", "t", "TRUE", "false", "F", "0", "5"} {
    if b, err := strconv.ParseBool(truth); err != nil {
        fmt.Printf("\n{%v}", err)
    } else {
        fmt.Print(b, " ")
    }
}
fmt.Println()

Output

true·true·true·false·false·false
{strconv.ParseBool:·parsing·"5":·invalid·syntax}

所有的strconv转换函数会返回一个转换后的值和一个error. 后则如果为nil, 则表示转换成功

x, err := strconv.ParseFloat("-99.7", 64)
fmt.Printf("%8T %6v %v\n", x, x, err)
y, err := strconv.ParseInt("71309", 10, 0)
fmt.Printf("%8T %6v %v\n", y, y, err)
z, err := strconv.Atoi("71309")
fmt.Printf("%8T %6v %v\n", z, z, err)

Output

·float64··-99.7·<nil>
···int64··71309·<nil>
·····int··71309·<nil>

strconv.ParseFloat(), strconv.ParseInt(), strconv.Atoi("ASCII" to int) 函数如我们所期望的一样。 strconv.Atoi(s)跟strconv.ParseInt(s,10,0)是一样的。 func ParseInt(s string, base int, bitSize int) (i int64, err error) 0, 8, 16, 32, and 64 correspond to int, int8, int16, int32, and int64. 如我们所想的那样strconv.ParseUint()函数将字符串转换为一个无符号整型(正整数), 如果字符串以"-",则转换失败。 同样如果字符存在前导或者后导空白字符,这些函数也都会转换失败。所以可以通过strings.TrimSpace()函数或者使用fmt package中的scan函数。 正常的, 浮点数的转换的字符串可以是标准的浮点数或者指数表示的浮点,比如"984", "424.019" 和 "3.916e-12".

s := strconv.FormatBool(z > 100)
fmt.Println(s)
i, err := strconv.ParseInt("0xDEED", 0, 32)
fmt.Println(i, err)
j, err := strconv.ParseInt("0707", 0, 32)
fmt.Println(j, err)
k, err := strconv.ParseInt("10111010001", 2, 32)

Output

true
57069·<nil>
455·<nil>
1489·<nil>

strconv.FormatBool()函数返回一个字符串表示的Boolean表左式,"true"或"false". strconv.ParseInt()函数将一个字符串的整型解析为 int64. 第二个参数是返回什么进制的数据,如果是0, 则基于第一个参数字符串中的进制表示, "0x" or "0X"为16进制, "0"为八进制. 在这里我们将隐式的解析一个16进制和一个8进制。同时明确的转换一个2进制。第三个参数是bit size, 表式返回的整型类型 0 表示的是int. 默认为int64)

i := 16769023
fmt.Println(strconv.Itoa(i))
fmt.Println(strconv.FormatInt(int64(i), 10))
fmt.Println(strconv.FormatInt(int64(i), 2))
fmt.Println(strconv.FormatInt(int64(i), 16))

Output

16769023
16769023
111111111101111111111111
ffdfff

strconv.Itoa()返回10进制的字符串. strconv.FormatInt()函数格式化一个int64类的整型到string. 第二个参数是指出字符串以什么进制输出(必须指定,可以为2-36)

s = "Alle ønsker å være fri."
quoted := strconv.Quote(s)
fmt.Println(quoted)
fmt.Println(strconv.Unquote(quoted))

Output

"Alle·\u00f8nsker·\u00e5·v\u00e6re·fri."
Alle·ønsker·å·være·fri.·<nil>

strconv.Quote() 函数返回一个双引号字符,并对不可打印的ASCII字符以及non-ASCII字符进行转义。strconv.Unquote()函数接受一个双引号字符串, 原始字符串(``重音符号)或者单引号的字符。并返回相应的没有引号的字符串和一个error(or nil)

API

func AppendBool(dst []byte, b bool) []byte

AppendBool将向dst中添加"true"或者"false", 并反回这个扩展后的dst.

var buffers []byte
fmt.Printf("%s", strconv.AppendBool(buffers, 10 > 1)) //true
fmt.Println(len(buffers)) //0
b := []byte("bool:")
b = strconv.AppendBool(b, true)
fmt.Println(string(b)) //bool:true

func AppendFloat(dst []byte, f float64, fmt byte, prec int, bitSize int) []byte

AppendFloat appends the string form of the floating-point number f, as generated by FormatFloat, to dst and returns the extended buffer.

b32 := []byte("float32:")
b32 = strconv.AppendFloat(b32, 3.1415926535, 'E', -1, 32)
fmt.Println(string(b32)) //float32:3.1415927E+00

b64 := []byte("float64:")
b64 = strconv.AppendFloat(b64, 3.1415926535, 'E', -1, 64)
fmt.Println(string(b64)) //float64:3.1415926535E+00

func AppendInt(dst []byte, i int64, base int) []byte

AppendInt appends the string form of the integer i, as generated by FormatInt, to dst and returns the extended buffer.

b10 := []byte("int (base 10):")
b10 = strconv.AppendInt(b10, -42, 10)
fmt.Println(string(b10)) //int (base 10):-42

b16 := []byte("int (base 16):")
b16 = strconv.AppendInt(b16, -42, 16)
fmt.Println(string(b16)) //int (base 16):-2a

func AppendQuote(dst []byte, s string) []byte

AppendQuote appends a double-quoted Go string literal representing s, as generated by Quote, to dst and returns the extended buffer.

b := []byte("quote:")
b = strconv.AppendQuote(b, `"Fran & Freddie's Diner"`)
fmt.Println(string(b)) //quote:"\"Fran & Freddie's Diner\""

func AppendQuoteRune(dst []byte, r rune) []byte

b := []byte("rune:")
b = strconv.AppendQuoteRune(b, '☺')
fmt.Println(string(b)) //rune:'☺'

func AppendQuoteRuneToASCII(dst []byte, r rune) []byte

AppendQuoteRuneToASCII appends a single-quoted Go character literal representing the rune, as generated by QuoteRuneToASCII, to dst and returns the extended buffer.

b := []byte("rune (ascii):")
b = strconv.AppendQuoteRuneToASCII(b, '☺')
fmt.Println(string(b)) // rune (ascii):'\u263a'

func AppendQuoteToASCII(dst []byte, s string) []byte

AppendQuoteToASCII appends a double-quoted Go string literal representing s, as generated by QuoteToASCII, to dst and returns the extended buffer.

b := []byte("quote (ascii):")
b = strconv.AppendQuoteToASCII(b, `"Fran & Freddie's Diner"`)
fmt.Println(string(b))
//quote (ascii):"\"Fran & Freddie's Diner\""

func AppendUint(dst []byte, i uint64, base int) []byte

AppendUint appends the string form of the unsigned integer i, as generated by FormatUint, to dst and returns the extended buffer.

b10 := []byte("uint (base 10):")
b10 = strconv.AppendUint(b10, 42, 10)
fmt.Println(string(b10)) //uint (base 10):42

b16 := []byte("uint (base 16):")
b16 = strconv.AppendUint(b16, 42, 16)
fmt.Println(string(b16)) //uint (base 16):2a

func Atoi(s string) (i int, err error)

Atoi is shorthand for ParseInt(s, 10, 0).

v := "10"
if s, err := strconv.Atoi(v); err == nil {
    fmt.Printf("%T, %v", s, s)
}
//int, 10

func CanBackquote(s string) bool

判断字符串s是否可以表示为一个单行的raw字符串(``), 即字符串中不能有控制符(除\t外)和(`);

fmt.Println(strconv.CanBackquote("Fran & Freddie's Diner ?")) //false
fmt.Println(strconv.CanBackquote("`can't backquote this")) //false
fmt.Println(strconv.CanBackquote("C:\\Windows\n")) //false

func FormatBool(b bool) string

FormatBool returns "true" or "false" according to the value of b

v := true
s := strconv.FormatBool(v)
fmt.Printf("%T, %v\n", s, s) //string, true

func FormatFloat(f float64, fmt byte, prec, bitSize int) string

FormatFloat将一个浮点数转换为string. fmt 可以是'b'(-ddddp±ddd, a binary exponent), 'e'(-d.dddde±dd, a decimal exponent), 'E' (-d.ddddE±dd, a decimal exponent), 'f' (-ddd.dddd, no exponent), 'g' ('e' for large exponents, 'f' otherwise), or 'G' ('E' for large exponents, 'f' otherwise).
prec是控制输出的精度. 对于'e', 'E', and 'f'来说,prec就是小数点后的数字位数(多少位),对于'g'和'G'则是整个的浮点数的位数。如果使用-1, 则返回此类型(float32或float64)最小位数
bitSize: 32(float32), 64(float64)

v := 3.1415926535
s32 := strconv.FormatFloat(v, 'E', -1, 32)
fmt.Printf("%T, %v\n", s32, s32)
//string, 3.1415927E+00
s64 := strconv.FormatFloat(v, 'E', -1, 64)
fmt.Printf("%T, %v\n", s64, s64)
//string, 3.1415926535E+00

func FormatInt(i int64, base int) string

FormatInt returns the string representation of i in the given base, for 2 <= base <= 36. The result uses the lower-case letters 'a' to 'z' for digit values >= 10.

v := int64(-42)

s10 := strconv.FormatInt(v, 10)
fmt.Printf("%T, %v\n", s10, s10) //string, -42

s16 := strconv.FormatInt(v, 16)
fmt.Printf("%T, %v\n", s16, s16) //string, -2a

func FormatUint(i uint64, base int) string

FormatUint returns the string representation of i in the given base, for 2 <= base <= 36. The result uses the lower-case letters 'a' to 'z' for digit values >= 10.

v := uint64(42)

s10 := strconv.FormatUint(v, 10)
fmt.Printf("%T, %v\n", s10, s10) //string, 42

s16 := strconv.FormatUint(v, 16)
fmt.Printf("%T, %v\n", s16, s16) //string, 2a

func IsPrint(r rune) bool

IsPrint reports whether the rune is defined as printable by Go, with the same definition as unicode.IsPrint: letters, numbers, punctuation, symbols and ASCII space.

c := strconv.IsPrint('\u263a')
fmt.Println(c) //true

bel := strconv.IsPrint('\007')
fmt.Println(bel) //false

func Itoa(i int) string

Itoa is shorthand for FormatInt(i, 10).

i := 10
s := strconv.Itoa(i)
fmt.Printf("%T, %v\n", s, s) //string, 10

func ParseBool(str string) (value bool, err error)

ParseBool returns the boolean value represented by the string. It accepts 1, t, T, TRUE, true, True, 0, f, F, FALSE, false, False. Any other value returns an error.

v := "true"
if s, err := strconv.ParseBool(v); err == nil {
    fmt.Printf("%T, %v\n", s, s) //bool, true
}

func ParseFloat(s string, bitSize int) (f float64, err error)

ParseFloat 将一个字符串s转换为浮点类型,bitSize可以为32或64。当bitSize=32时,其结果依然是float64. 但它的返回值是可以转变为32,而不会产生变化(在float32范围内)

v := "3.1415926535"
if s, err := strconv.ParseFloat(v, 32); err == nil {
    fmt.Printf("%T, %v\n", s, s)
    //float64, 3.1415927410125732
}
if s, err := strconv.ParseFloat(v, 64); err == nil {
    fmt.Printf("%T, %v\n", s, s)
    //float64, 3.1415926535
}

func ParseInt(s string, base int, bitSize int) (i int64, err error)

ParseInt 解析字符串s到int63, 变量base可以为2 - 36, 用于指定返回的数字进制。 如果base == 0, 则根据字符串的前缀来做判断,比如s的前缀为0x,则返回一个16进制的,如果前缀为0,则返回8进制,其它则10进制。
bitSize参数用于返回的数字类型,可以为0,8,16,32, 64分别对应int, int8, int16, int32, int64
err是*strconv.NumError类型,err.Num等于s. 如果s为空或者是个非有效的数子, err的错误信息是ErrSyntax(invalid syntax), 并且返回的值i为0. 如果value不在给定的bitSize范围内,则报的错误信息是ErrRange(value out of range),返回的值是给定的类型的最大值(int8, 最大值为127, 则你要解析"1000")

v32 := "-354634382"
if s, err := strconv.ParseInt(v32, 10, 32); err == nil {
    fmt.Printf("%T, %v\n", s, s)
    //int64, -354634382
}

v64 := "-3546343826724305832"
if s, err := strconv.ParseInt(v64, 10, 64); err == nil {
    fmt.Printf("%T, %v\n", s, s)
    //int64, -3546343826724305832
}

func ParseUint(s string, base int, bitSize int) (n uint64, err error)

ParseUint is like ParseInt but for unsigned numbers.

v := "42"
if s, err := strconv.ParseUint(v, 10, 32); err == nil {
    fmt.Printf("%T, %v\n", s, s) //uint64, 42
}
if s, err := strconv.ParseUint(v, 10, 64); err == nil {
    fmt.Printf("%T, %v\n", s, s) //uint64, 42
}

func Quote(s string) string

对s加以一个双引号, 并对控制符(\t, \n, \xFF, \u0100) 和非打印字符进行转义

s := strconv.Quote(`"Fran & Freddie's Diner    ☺"`)
fmt.Println(s) // "\"Fran & Freddie's Diner\t☺\""

func QuoteRune(r rune) string

返回由单引号包围的字符。并对控制符(\t, \n, \xFF, \u0100) 和非打印字符进行转义

s := strconv.QuoteRune('☺')
fmt.Println(s) //'☺'

func QuoteRuneToASCII

对控制符(\t, \n, \xFF, \u0100), 非打印字符,以及non-ASCII进行转义

s := strconv.QuoteRuneToASCII('☺')
fmt.Println(s) // '\u263a'

func QuoteToASCII(s string) string

返回双引号括起来的字符串. 并对控制符(\t, \n, \xFF, \u0100), 非打印字符,以及non-ASCII进行转

s := strconv.QuoteToASCII(`"Fran & Freddie's Diner    ☺"`)
fmt.Println(s) //"\"Fran & Freddie's Diner\t\u263a\""

func Unquote(s string) (t string, err error)

Unquote 取消掉s中的单引号,双引号,或者`

test := func(s string) {
    t, err := strconv.Unquote(s)
    if err != nil {
        fmt.Printf("Unquote(%#v): %v\n", s, err)
    } else {
        fmt.Printf("Unquote(%#v) = %v\n", s, t)
    }
}

s := `\"Fran & Freddie's Diner\t\u263a\"\"`
// If the string doesn't have quotes, it can't be unquoted.
test(s) 
// invalid syntax, 因为传入的值 为\"Fran & Freddie's Diner\t\u263a\"\"
// 没有包含 ``或者"",所以发生错误 
test("`" + s + "`")
test(`"` + s + `"`)
test(`'\u263a'`)

Output

Unquote("\\\"Fran & Freddie's Diner\\t\\u263a\\\"\\\""): invalid syntax
Unquote("`\\\"Fran & Freddie's Diner\\t\\u263a\\\"\\\"`") = \"Fran & Freddie's Diner\t\u263a\"\"
Unquote("\"\\\"Fran & Freddie's Diner\\t\\u263a\\\"\\\"\"") = "Fran & Freddie's Diner    ☺""
Unquote("'\\u263a'") = ☺

type NumError

type NumError struct {
    Func string // the failing function (ParseBool, ParseInt, ParseUint, ParseFloat)
    Num  string // the input
    Err  error  // the reason the conversion failed (ErrRange, ErrSyntax)
}

A NumError records a failed conversion.

str := "Not a number"
if _, err := strconv.ParseFloat(str, 64); err != nil {
    e := err.(*strconv.NumError)
    fmt.Println("Func:", e.Func)
    fmt.Println("Num:", e.Num)
    fmt.Println("Err:", e.Err)
    fmt.Println(err)
}

Output

Func: ParseFloat
Num: Not a number
Err: invalid syntax
strconv.ParseFloat: parsing "Not a number": invalid syntax

func (*NumError) Error