In the following code, I iterate over a string
rune by rune, but I'll actually need an int
to perform some checksum calculation. Do I really need to encode the rune
into a []byte
, then convert it to a string
and then use Atoi
to get an int
out of the rune
? Is this the idiomatic way to do it?
// The string `s` only contains digits. var factor int for i, c := range s[:12] { if i % 2 == 0 { factor = 1 } else { factor = 3 } buf := make([]byte, 1) _ = utf8.EncodeRune(buf, c) value, _ := strconv.Atoi(string(buf)) sum += value * factor }
On the playground: http://play.golang.org/p/noWDYjn5rJ
14 Answers
The problem is simpler than it looks. You convert a rune
value to an int
value with int(r)
. But your code implies you want the integer value out of the ASCII (or UTF-8) representation of the digit, which you can trivially get with r - '0'
as a rune
, or int(r - '0')
as an int
. Be aware that out-of-range runes will corrupt that logic.
For example, sum += (int(c) - '0') * factor
,
package main import ( "fmt" "strconv" "unicode/utf8" ) func main() { s := "9780486653556" var factor, sum1, sum2 int for i, c := range s[:12] { if i%2 == 0 { factor = 1 } else { factor = 3 } buf := make([]byte, 1) _ = utf8.EncodeRune(buf, c) value, _ := strconv.Atoi(string(buf)) sum1 += value * factor sum2 += (int(c) - '0') * factor } fmt.Println(sum1, sum2) }
Output:
124 124
3why don't you do only "string(rune)".
s:="12345678910" var factor,sum int for i,x:=range s{ if i%2==0{ factor=1 }else{ factor=3 } xstr:=string(x) //x is rune converted to string xint,_:=strconv.Atoi(xstr) sum+=xint*factor } fmt.Println(sum)
val, _ := strconv.Atoi(string(v))
Where v is a rune
More concise but same idea as above
ncG1vNJzZmirpJawrLvVnqmfpJ%2Bse6S7zGiorp2jqbawutJoaWprYmd%2BeH%2BOnKanrpWnwW6%2B1KecZqyfYravwA%3D%3D